{
 "cells": [
  {
   "cell_type": "markdown",
   "metadata": {},
   "source": [
    "### Title: #Partition List"
   ]
  },
  {
   "cell_type": "markdown",
   "metadata": {},
   "source": [
    "Difficulty: #Medium"
   ]
  },
  {
   "cell_type": "markdown",
   "metadata": {},
   "source": [
    "Category Title: #Algorithms"
   ]
  },
  {
   "cell_type": "markdown",
   "metadata": {},
   "source": [
    "Tag Slug: #linked-list #two-pointers"
   ]
  },
  {
   "cell_type": "markdown",
   "metadata": {},
   "source": [
    "Name Translated: #链表 #双指针"
   ]
  },
  {
   "cell_type": "markdown",
   "metadata": {},
   "source": [
    "Solution Name: partition"
   ]
  },
  {
   "cell_type": "markdown",
   "metadata": {},
   "source": [
    "Translated Title: #分隔链表"
   ]
  },
  {
   "cell_type": "markdown",
   "metadata": {},
   "source": [
    "Translated Content:\n",
    "<p>给你一个链表的头节点 <code>head</code> 和一个特定值<em> </em><code>x</code> ，请你对链表进行分隔，使得所有 <strong>小于</strong> <code>x</code> 的节点都出现在 <strong>大于或等于</strong> <code>x</code> 的节点之前。</p>\n",
    "\n",
    "<p>你应当 <strong>保留</strong> 两个分区中每个节点的初始相对位置。</p>\n",
    "\n",
    "<p> </p>\n",
    "\n",
    "<p><strong>示例 1：</strong></p>\n",
    "<img alt=\"\" src=\"https://assets.leetcode.com/uploads/2021/01/04/partition.jpg\" style=\"width: 662px; height: 222px;\" />\n",
    "<pre>\n",
    "<strong>输入：</strong>head = [1,4,3,2,5,2], x = 3\n",
    "<strong>输出</strong>：[1,2,2,4,3,5]\n",
    "</pre>\n",
    "\n",
    "<p><strong>示例 2：</strong></p>\n",
    "\n",
    "<pre>\n",
    "<strong>输入：</strong>head = [2,1], x = 2\n",
    "<strong>输出</strong>：[1,2]\n",
    "</pre>\n",
    "\n",
    "<p> </p>\n",
    "\n",
    "<p><strong>提示：</strong></p>\n",
    "\n",
    "<ul>\n",
    "\t<li>链表中节点的数目在范围 <code>[0, 200]</code> 内</li>\n",
    "\t<li><code>-100 <= Node.val <= 100</code></li>\n",
    "\t<li><code>-200 <= x <= 200</code></li>\n",
    "</ul>\n"
   ]
  },
  {
   "cell_type": "markdown",
   "metadata": {},
   "source": [
    "Description: [partition-list](https://leetcode.cn/problems/partition-list/description/)"
   ]
  },
  {
   "cell_type": "markdown",
   "metadata": {},
   "source": [
    "Solutions: [partition-list](https://leetcode.cn/problems/partition-list/solutions/)"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "test_cases = ['[1,4,3,2,5,2]\\n3', '[2,1]\\n2']"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "from typing import List\n",
    "import collections\n",
    "\n",
    "class Solution:\n",
    "    def partitionString(self, s: str) -> int:\n",
    "        nSubs: int = 1\n",
    "        seen: Set[str] = set()\n",
    "\n",
    "        for c in s:\n",
    "            if c not in seen:\n",
    "                seen.add(c)\n",
    "            else:\n",
    "                nSubs += 1\n",
    "                seen = set([c])\n",
    "\n",
    "        return nSubs"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "from typing import List\n",
    "import collections\n",
    "\n",
    "class Solution:\n",
    "    def partitionString(self, s: str) -> int:\n",
    "        res=1\n",
    "        cnt=0\n",
    "        for c in s:\n",
    "            if cnt&1<<(ord(c)-ord('a')):\n",
    "                cnt=1<<(ord(c)-ord('a'))\n",
    "                res +=1\n",
    "            else:\n",
    "                cnt |=1<<(ord(c)-ord('a'))\n",
    "        return res\n"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "from typing import List\n",
    "import collections\n",
    "\n",
    "class Solution:\n",
    "    def partitionString(self, s: str) -> int:\n",
    "        count = 1\n",
    "        tmp = \"\"\n",
    "        for i in s:\n",
    "            if i in tmp:\n",
    "                count += 1\n",
    "                tmp = i\n",
    "                continue\n",
    "            tmp = tmp + i\n",
    "        return count"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "from typing import List\n",
    "import collections\n",
    "\n",
    "class Solution:\n",
    "    def partitionString(self, s: str) -> int:\n",
    "        mp = Counter()\n",
    "        ans = 0\n",
    "        for c in s:\n",
    "            if len(mp) == 0:\n",
    "                ans += 1\n",
    "                mp[c] = 1\n",
    "                continue\n",
    "            if c in mp:\n",
    "                ans += 1\n",
    "                mp.clear()\n",
    "            mp[c] = 1\n",
    "        return ans"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "from typing import List\n",
    "import collections\n",
    "\n",
    "class Solution:\n",
    "    def partitionString(self, s: str) -> int:\n",
    "        ha=[]\n",
    "        count=0\n",
    "        for ch in s:\n",
    "            if ch in ha:\n",
    "                count+=1\n",
    "                ha=[ch]\n",
    "            else:\n",
    "                ha.append(ch)\n",
    "        return count+1\n"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "from typing import List\n",
    "import collections\n",
    "\n",
    "class Solution:\n",
    "    def partitionString(self, s: str) -> int:\n",
    "        res=1\n",
    "        cnt=set()\n",
    "        for c in s:\n",
    "            if c not in cnt:\n",
    "                cnt.add(c)\n",
    "            else:\n",
    "                cnt=set()\n",
    "                cnt.add(c)\n",
    "                res+=1\n",
    "        return res"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "from typing import List\n",
    "import collections\n",
    "\n",
    "class Solution:\n",
    "    def partitionString(self, s: str) -> int:\n",
    "        j, cnt, window = 0, 0, []\n",
    "        while j < len(s):\n",
    "            if s[j] in window: \n",
    "                cnt += 1\n",
    "                window = []  \n",
    "            window.append(s[j])\n",
    "            j += 1\n",
    "        return cnt + 1  \n",
    "\n"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "from typing import List\n",
    "import collections\n",
    "\n",
    "class Solution:\n",
    "    def partitionString(self, s: str) -> int:\n",
    "        r=0\n",
    "        t=set()\n",
    "        res=0\n",
    "        while r<len(s):\n",
    "            if s[r] not in t:\n",
    "                t.add(s[r])\n",
    "            else:\n",
    "                res+=1\n",
    "                t.clear()\n",
    "                t.add(s[r])\n",
    "            r+=1\n",
    "        return res+1\n",
    "\n",
    "\n",
    "            "
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "from typing import List\n",
    "import collections\n",
    "\n",
    "class Solution:\n",
    "    def partitionString(self, s: str) -> int:\n",
    "        res=1\n",
    "        cnt=''\n",
    "        for c in s:\n",
    "            if c not in cnt:\n",
    "                cnt +=c\n",
    "            else:\n",
    "                cnt=c\n",
    "                res+=1\n",
    "        return res"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "from typing import List\n",
    "import collections\n",
    "\n",
    "class Solution:\n",
    "    def partitionString(self, s: str) -> int:\n",
    "        # 使用集合进行辅助\n",
    "        i = 0\n",
    "        n = len(s)\n",
    "        total_num = 0\n",
    "        while i < n:\n",
    "            se = set(s[i])\n",
    "            j = i + 1\n",
    "            while j < n:\n",
    "                if s[j] in se:\n",
    "                    # 此时出现重复的，因此需要更新i\n",
    "                    i = j\n",
    "                    total_num += 1\n",
    "                    break\n",
    "                else:\n",
    "                    se.add(s[j])\n",
    "                    j += 1\n",
    "            # 判断j是否为n\n",
    "            if j == n:\n",
    "                total_num += 1\n",
    "                break\n",
    "        return total_num\n",
    "            "
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "from typing import List\n",
    "import collections\n",
    "\n",
    "class Solution:\n",
    "    def partitionString(self, s: str) -> int:\n",
    "        ans = 1\n",
    "        st = set()\n",
    "        for c in s:\n",
    "            if c not in st:\n",
    "                st.add(c)\n",
    "            else:\n",
    "                ans += 1\n",
    "                st = {c}\n",
    "        return ans"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "from typing import List\n",
    "import collections\n",
    "\n",
    "class Solution:\n",
    "    def partitionString(self, s: str) -> int:\n",
    "        res = 1\n",
    "        tmp = ''\n",
    "        for c in s:\n",
    "            if c not in tmp:\n",
    "                tmp += c\n",
    "            else:\n",
    "                tmp = c\n",
    "                res += 1\n",
    "        return res"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "from typing import List\n",
    "import collections\n",
    "\n",
    "class Solution:\n",
    "    def partitionString(self, s: str) -> int:\n",
    "        # 贪心\n",
    "        ans = 0\n",
    "        m = set()\n",
    "        for c in s:\n",
    "            if c in m:\n",
    "                ans += 1\n",
    "                m.clear()\n",
    "            m.add(c)\n",
    "            \n",
    "        return ans + 1"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "from typing import List\n",
    "import collections\n",
    "\n",
    "class Solution:\n",
    "    def partitionString(self, s: str) -> int:\n",
    "        ans = 1\n",
    "        nowset = set()\n",
    "        left = 0\n",
    "        lens = len(s)\n",
    "        for i in range(lens):\n",
    "            if s[i] not in nowset:\n",
    "                nowset.add(s[i])\n",
    "            else:\n",
    "                ans += 1\n",
    "                nowset.clear()\n",
    "                nowset.add(s[i])\n",
    "        # if len(nowset) > 0:\n",
    "        #     ans += 1\n",
    "        return ans"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "from typing import List\n",
    "import collections\n",
    "\n",
    "class Solution:\n",
    "    def partitionString(self, s: str) -> int:\n",
    "        vis = set()\n",
    "        ans = 0\n",
    "        for c in s:\n",
    "            if c in vis:\n",
    "                ans += 1\n",
    "                vis = set([c])\n",
    "            else:\n",
    "                vis.add(c)\n",
    "        return ans + 1"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "from typing import List\n",
    "import collections\n",
    "\n",
    "class Solution:\n",
    "    def partitionString(self, s: str) -> int:\n",
    "        ans=0\n",
    "        cur=''\n",
    "        for i in s:\n",
    "            if i not in cur:\n",
    "                cur+=i\n",
    "            else:\n",
    "                ans+=1\n",
    "                cur=i\n",
    "        return ans+1\n"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "from typing import List\n",
    "import collections\n",
    "\n",
    "class Solution:\n",
    "    def partitionString(self, s: str) -> int:\n",
    "        ans=1\n",
    "\n",
    "        c=Counter()\n",
    "        for i in range (0,len(s)):\n",
    "            x=s[i]\n",
    "            c[x]+=1\n",
    "            if c[x]==2:\n",
    "                ans+=1\n",
    "                c=Counter()\n",
    "                c[x]=1\n",
    "        return ans"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "from typing import List\n",
    "import collections\n",
    "\n",
    "class Solution:\n",
    "    def partitionString(self, s: str) -> int:\n",
    "        appear = set()\n",
    "        ans = 1\n",
    "        for c in s:\n",
    "            if c in appear:\n",
    "                appear.clear()\n",
    "                ans += 1\n",
    "            appear.add(c)\n",
    "        return ans\n",
    "\n"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "from typing import List\n",
    "import collections\n",
    "\n",
    "class Solution:\n",
    "    def partitionString(self, s: str) -> int:\n",
    "        count = 0\n",
    "        d = set()\n",
    "        for i in s:\n",
    "            if i not in d:\n",
    "                d.add(i)\n",
    "            else:\n",
    "                count += 1\n",
    "                d.clear()\n",
    "                d.add(i)\n",
    "        return count + 1"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "from typing import List\n",
    "import collections\n",
    "\n",
    "class Solution:\n",
    "    def partitionString(self, s: str) -> int:\n",
    "        count=0\n",
    "        a=[]\n",
    "        for i in s:\n",
    "            if i in a :\n",
    "                a=[]\n",
    "                count+=1\n",
    "            a.append(i)\n",
    "        return count+1\n"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "from typing import List\n",
    "import collections\n",
    "\n",
    "class Solution:\n",
    "    def partitionString(self, s: str) -> int:\n",
    "        ret = 0\n",
    "        s1 = ''\n",
    "        for value in s:\n",
    "            if value in s1:\n",
    "                ret = ret + 1\n",
    "                s1 = ''\n",
    "            s1 += value\n",
    "\n",
    "        return ret + 1"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "from typing import List\n",
    "import collections\n",
    "\n",
    "class Solution:\n",
    "    def partitionString(self, s: str) -> int:\n",
    "        start,ans = 0,0\n",
    "        for i in range(1,len(s)):\n",
    "            if s[i] in s[start:i]:\n",
    "                ans += 1\n",
    "                start = i\n",
    "        return ans+1\n",
    "            \n"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "from typing import List\n",
    "import collections\n",
    "\n",
    "class Solution:\n",
    "    def partitionString(self, s: str) -> int:\n",
    "        set_char = set()\n",
    "        num_substr = 1\n",
    "        for char in s:\n",
    "            if char in set_char:\n",
    "                set_char = set(char)\n",
    "                num_substr += 1\n",
    "            else:\n",
    "                set_char.add(char)\n",
    "        return num_substr"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "from typing import List\n",
    "import collections\n",
    "\n",
    "class Solution:\n",
    "    def partitionString(self, s: str) -> int:\n",
    "        current_chars = set()  # 用于跟踪当前子字符串中的字符\n",
    "        count = 0  # 子字符串的数量\n",
    "\n",
    "        for char in s:\n",
    "            if char in current_chars:\n",
    "                count += 1\n",
    "                current_chars.clear()\n",
    "            current_chars.add(char)\n",
    "\n",
    "        if current_chars:  # 如果还有剩余的字符，需要为其增加一个子字符串\n",
    "            count += 1\n",
    "\n",
    "        return count"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "from typing import List\n",
    "import collections\n",
    "\n",
    "class Solution:\n",
    "    def partitionString(self, s: str) -> int:\n",
    "        res = 1\n",
    "        hashtable = set()\n",
    "        hashtable.add(s[0])\n",
    "        for char in s[1:]:\n",
    "            if char not in hashtable:\n",
    "                hashtable.add(char)\n",
    "            else:\n",
    "                hashtable =set()\n",
    "                hashtable.add(char)\n",
    "                res +=1\n",
    "        return res\n"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "from typing import List\n",
    "import collections\n",
    "\n",
    "class Solution:\n",
    "    def partitionString(self, s: str) -> int:\n",
    "        current_chars = set()  # 用于跟踪当前子字符串中的字符\n",
    "        count = 0  # 子字符串的数量\n",
    "\n",
    "        for char in s:\n",
    "            if char in current_chars:\n",
    "                count += 1\n",
    "                current_chars.clear()\n",
    "            current_chars.add(char)\n",
    "\n",
    "        if current_chars:  # 如果还有剩余的字符，需要为其增加一个子字符串\n",
    "            count += 1\n",
    "\n",
    "        return count"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "from typing import List\n",
    "import collections\n",
    "\n",
    "class Solution:\n",
    "    def partitionString(self, s: str) -> int:\n",
    "        left=0\n",
    "        ans=0\n",
    "        letterMapping={}\n",
    "        for i,c in enumerate(s):\n",
    "            if c in letterMapping:\n",
    "                if left<=letterMapping[c]:\n",
    "                    ans+=1\n",
    "                    left=i\n",
    "            letterMapping[c]=i\n",
    "        return ans+1\n"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "from typing import List\n",
    "import collections\n",
    "\n",
    "class Solution:\n",
    "    def partitionString(self, s: str) -> int:\n",
    "        ans = 1\n",
    "        vis = \"\"\n",
    "        for ch in s:\n",
    "            if ch in vis:\n",
    "                vis = \"\"\n",
    "                ans += 1\n",
    "            vis += ch\n",
    "        return ans\n",
    "\n",
    "\n",
    "\n",
    "        # dic = set()\n",
    "        # ans = 0\n",
    "        # for ch in s:\n",
    "        #     if ch in dic:\n",
    "        #         ans += 1\n",
    "        #         dic = set(ch)\n",
    "        #     else:\n",
    "        #         dic.add(ch)\n",
    "        # return ans + 1 "
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "from typing import List\n",
    "import collections\n",
    "\n",
    "class Solution:\n",
    "    def partitionString(self, s: str) -> int:\n",
    "        cur = ''\n",
    "        res = 1\n",
    "        for i in s:\n",
    "            if i in cur:\n",
    "                res += 1\n",
    "                cur = i\n",
    "            else:\n",
    "                cur += i\n",
    "        return res"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "from typing import List\n",
    "import collections\n",
    "\n",
    "class Solution:\n",
    "    def partitionString(self, s: str) -> int:\n",
    "        ans = 1\n",
    "        vis = set()\n",
    "        for i, c in enumerate(s):\n",
    "            if c in vis:\n",
    "                vis.clear()\n",
    "                ans += 1\n",
    "            vis.add(c)\n",
    "        return ans"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "from typing import List\n",
    "import collections\n",
    "\n",
    "class Solution:\n",
    "    def partitionString(self, s: str) -> int:\n",
    "        # 经典的滑动窗口\n",
    "        j, cnt, window = 0, 0, set()\n",
    "        while j < len(s):\n",
    "            if s[j] in window:  # 出现重复值\n",
    "                cnt += 1\n",
    "                window = set()  # 清空窗口\n",
    "            window.add(s[j])\n",
    "            j += 1\n",
    "        return cnt + 1  # 加上最后的一个区间\n",
    "\n"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "from typing import List\n",
    "import collections\n",
    "\n",
    "class Solution:\n",
    "    def partitionString(self, s: str) -> int:\n",
    "        ans = 0\n",
    "        temp = set()\n",
    "        for i in s:\n",
    "            if i not in temp:\n",
    "                temp.add(i)\n",
    "            else:\n",
    "                ans += 1\n",
    "                temp = set(i)\n",
    "        return ans + 1"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "from typing import List\n",
    "import collections\n",
    "\n",
    "class Solution:\n",
    "    def partitionString(self, s: str) -> int:\n",
    "        dic={}\n",
    "        result=0\n",
    "        for i in range(len(s)):\n",
    "            if s[i] not in dic:\n",
    "                dic[s[i]]=1\n",
    "            else:\n",
    "                result+=1\n",
    "                dic={s[i]:1}\n",
    "        \n",
    "        return result+1\n",
    "            "
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "from typing import List\n",
    "import collections\n",
    "\n",
    "class Solution:\n",
    "    def partitionString(self, s: str) -> int:\n",
    "        集合 = set()\n",
    "        最少次数 = 1\n",
    "        for i in s:\n",
    "            if i in 集合:\n",
    "                最少次数 += 1\n",
    "                集合.clear()\n",
    "            集合.add(i)\n",
    "        return 最少次数"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "from typing import List\n",
    "import collections\n",
    "\n",
    "class Solution:\n",
    "    def partitionString(self, s: str) -> int:\n",
    "        j, cnt, window = 0, 0, {}\n",
    "        while j < len(s):\n",
    "            if s[j] in window: \n",
    "                cnt += 1\n",
    "                window = {}  \n",
    "            window[s[j]]=0\n",
    "            j += 1\n",
    "        return cnt + 1  \n",
    "\n"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "from typing import List\n",
    "import collections\n",
    "\n",
    "class Solution:\n",
    "    def partitionString(self, s: str) -> int:\n",
    "        n=len(s)\n",
    "        i=0\n",
    "        ans=0\n",
    "        while i<n:\n",
    "            t=set()\n",
    "            while i<n and s[i] not in t:\n",
    "                t.add(s[i])\n",
    "                i+=1\n",
    "            ans+=1\n",
    "        return ans"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "from typing import List\n",
    "import collections\n",
    "\n",
    "class Solution:\n",
    "    def partitionString(self, s: str) -> int:\n",
    "        res = 0\n",
    "        visit = set()\n",
    "        for c in s:\n",
    "            if c in visit:\n",
    "                res += 1\n",
    "                visit = set()\n",
    "            visit.add(c)\n",
    "        return res if visit == set() else res + 1"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "from typing import List\n",
    "import collections\n",
    "\n",
    "class Solution:\n",
    "    def partitionString(self, s: str) -> int:\n",
    "        ans = 0\n",
    "        visited = set()\n",
    "        for ch in s:\n",
    "            if ch in visited:\n",
    "                ans += 1\n",
    "                visited = set()\n",
    "            visited.add(ch)\n",
    "        return ans + 1"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "from typing import List\n",
    "import collections\n",
    "\n",
    "class Solution:\n",
    "    def partitionString(self, s: str) -> int:\n",
    "        start,ans = 0,0\n",
    "        for i in range(1,len(s)):\n",
    "            if s[i] in s[start:i]:\n",
    "                ans += 1\n",
    "                start = i\n",
    "        return ans+1\n",
    "            \n"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "from typing import List\n",
    "import collections\n",
    "\n",
    "class Solution:\n",
    "    def partitionString(self, s: str) -> int:\n",
    "        cnt = 1\n",
    "        str_set = set()\n",
    "        for char in s:\n",
    "            if char in str_set:\n",
    "                cnt += 1\n",
    "                str_set.clear()\n",
    "            str_set.add(char)\n",
    "        return cnt"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "from typing import List\n",
    "import collections\n",
    "\n",
    "class Solution:\n",
    "    def partitionString(self, s: str) -> int:\n",
    "        index = 0\n",
    "        cur = []\n",
    "        result = 0\n",
    "        while index < len(s):\n",
    "            if s[index] not in cur:\n",
    "                cur.append(s[index])\n",
    "            else:\n",
    "                result += 1\n",
    "                cur = []\n",
    "                continue\n",
    "            index += 1\n",
    "        if cur:\n",
    "            result += 1\n",
    "        return result"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "from typing import List\n",
    "import collections\n",
    "\n",
    "class Solution:\n",
    "    def partitionString(self, s: str) -> int:\n",
    "        \"\"\"\n",
    "        集合 = set()\n",
    "        最少次数 = 1\n",
    "        for i in s:\n",
    "            if i in 集合:\n",
    "                最少次数 += 1\n",
    "                集合.clear()\n",
    "            集合.add(i)\n",
    "        return 最少次数\n",
    "        \"\"\"\n",
    "        #位运算\n",
    "        集合 = 0\n",
    "        最少次数 = 1\n",
    "        for i in s:\n",
    "            i  = ord(i)-97\n",
    "            if 集合 >> i & 1:\n",
    "                最少次数 += 1\n",
    "                集合 = 0\n",
    "            集合 |= 1<<i\n",
    "        return 最少次数\n"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "from typing import List\n",
    "import collections\n",
    "\n",
    "class Solution:\n",
    "    def partitionString(self, s: str) -> int:\n",
    "        temp = [0] * 26\n",
    "        res = 0\n",
    "        for i in range(len(s)):\n",
    "            num = ord(s[i]) - ord(\"a\")\n",
    "            if temp[num] == 0:\n",
    "                temp[num] += 1\n",
    "            else:\n",
    "                del(temp)\n",
    "                res += 1\n",
    "                temp = [0] * 26\n",
    "                temp[num] = 1\n",
    "        return res + 1"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "from typing import List\n",
    "import collections\n",
    "\n",
    "class Solution:\n",
    "    def partitionString(self, s: str) -> int:\n",
    "        '''\n",
    "        use set: \n",
    "        1. let res is result we want, temp = set()\n",
    "        2. iterate s:\n",
    "            (1)if charcter in set, then res + 1, and set temp to empty\n",
    "            (2) add charcter to set\n",
    "        3. return res +1\n",
    "\n",
    "        O(len(s))\n",
    "\n",
    "        '''\n",
    "\n",
    "        res = 0\n",
    "        temp = set()\n",
    "\n",
    "        for char in s:\n",
    "            if char in temp:\n",
    "                temp = set()\n",
    "                res += 1\n",
    "            temp.add(char)\n",
    "        \n",
    "        return res+1"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "from typing import List\n",
    "import collections\n",
    "\n",
    "class Solution:\n",
    "    def partitionString(self, s: str) -> int:\n",
    "        cont=0\n",
    "        n=len(s)\n",
    "        dp=[]\n",
    "        for i in range(n):\n",
    "            if s[i] in dp:\n",
    "                dp.clear()\n",
    "                cont+=1\n",
    "            dp.append(s[i])\n",
    "        return cont+1"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "from typing import List\n",
    "import collections\n",
    "\n",
    "class Solution:\n",
    "    def partitionString(self, s: str) -> int:\n",
    "        cur = []\n",
    "        res = 1\n",
    "        for i, c in enumerate(s):\n",
    "            if c in set(cur):\n",
    "                res += 1\n",
    "                print(cur)\n",
    "                cur = []\n",
    "            cur.append(c)\n",
    "        return res\n"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "from typing import List\n",
    "import collections\n",
    "\n",
    "class Solution:\n",
    "    def partitionString(self, s: str) -> int:\n",
    "        res, mark = 1, set()\n",
    "        for c in s:\n",
    "            if c in mark:\n",
    "                res += 1\n",
    "                mark.clear()\n",
    "            mark.add(c)\n",
    "        return res"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "from typing import List\n",
    "import collections\n",
    "\n",
    "class Solution:\n",
    "    def partitionString(self, s: str) -> int:\n",
    "        # 经典的滑动窗口\n",
    "        j, cnt, window = 0, 0, set()\n",
    "        while j < len(s):\n",
    "            if s[j] in window:  # 出现重复值\n",
    "                cnt += 1\n",
    "                window = set()  # 清空窗口\n",
    "            window.add(s[j])\n",
    "            j += 1\n",
    "        return cnt + 1  # 加上最后的一个区间\n",
    "\n"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "from typing import List\n",
    "import collections\n",
    "\n",
    "class Solution:\n",
    "    def partitionString(self, s: str) -> int:\n",
    "        n = len(s)\n",
    "        ans, t = 0, set()\n",
    "        for ch in s:\n",
    "            if ch not in t:\n",
    "                t.add(ch)\n",
    "            else:\n",
    "                ans += 1\n",
    "                t = set([ch])\n",
    "        if t:\n",
    "            ans += 1\n",
    "        return ans"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "from typing import List\n",
    "import collections\n",
    "\n",
    "class Solution:\n",
    "    def partitionString(self, s: str) -> int:\n",
    "        '''\n",
    "        use set: \n",
    "        1. let res is result we want, temp = set()\n",
    "        2. iterate s:\n",
    "            (1)if charcter in set, then res + 1, and set temp to empty\n",
    "            (2) if not, add charcter to set\n",
    "        3. return result\n",
    "\n",
    "        O(len(s))\n",
    "\n",
    "        '''\n",
    "\n",
    "        res = 0\n",
    "        temp = set()\n",
    "\n",
    "        for char in s:\n",
    "            if char in temp:\n",
    "                temp = set()\n",
    "                res += 1\n",
    "            temp.add(char)\n",
    "        \n",
    "        return res+1"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "from typing import List\n",
    "import collections\n",
    "\n",
    "class Solution:\n",
    "    def partitionString(self, s: str) -> int:\n",
    "        d = defaultdict(int)\n",
    "        cnt = 1\n",
    "        left = 0\n",
    "        while left < len(s):\n",
    "            if d[s[left]] == 1:\n",
    "                d = defaultdict(int)\n",
    "                cnt += 1\n",
    "            d[s[left]] += 1\n",
    "            left += 1\n",
    "        return cnt                                        "
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "from typing import List\n",
    "import collections\n",
    "\n",
    "class Solution:\n",
    "    def partitionString(self, s: str) -> int:\n",
    "        record = {}\n",
    "        count = 1\n",
    "        for i in range(len(s)):\n",
    "            c = s[i]\n",
    "            if c not in record:\n",
    "                record[c]=1\n",
    "            else:\n",
    "                record = {}\n",
    "                record[c] = 1\n",
    "                count+=1\n",
    "\n",
    "        return count\n",
    "            "
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "from typing import List\n",
    "import collections\n",
    "\n",
    "class Solution:\n",
    "    def partitionString(self, s: str) -> int:\n",
    "        mask, res = 0, 1\n",
    "        ordA = ord('a')\n",
    "        for c in s:\n",
    "            m = 1<<(ord(c) - ordA)\n",
    "            if mask & m:\n",
    "                mask = 0\n",
    "                res += 1\n",
    "            mask |= m\n",
    "        return res\n"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "from typing import List\n",
    "import collections\n",
    "\n",
    "class Solution:\n",
    "    def partitionString(self, s: str) -> int:\n",
    "        n = len(s)\n",
    "        \n",
    "        res = 0\n",
    "        hashset = set()\n",
    "\n",
    "        i = 0\n",
    "        while i < n:\n",
    "            hashset.add(s[i])\n",
    "            res += 1\n",
    "            \n",
    "            j = i + 1\n",
    "            while j < n and s[j] not in hashset:\n",
    "                hashset.add(s[j])\n",
    "                j += 1\n",
    "                \n",
    "            i = j\n",
    "            hashset.clear()\n",
    "            \n",
    "        return res\n"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "from typing import List\n",
    "import collections\n",
    "\n",
    "class Solution:\n",
    "    def partitionString(self, s: str) -> int:\n",
    "        count=1\n",
    "        temp=\"\"\n",
    "        for i in s:\n",
    "            if i not in temp:\n",
    "                temp+=i\n",
    "            else:\n",
    "                count+=1\n",
    "                temp=i\n",
    "        return count\n",
    "\n",
    "\n"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "from typing import List\n",
    "import collections\n",
    "\n",
    "class Solution:\n",
    "    def partitionString(self, s: str) -> int:\n",
    "        tmp_s = \"\"\n",
    "        cn = 0\n",
    "        for ss in s:\n",
    "            print(ss, tmp_s)\n",
    "            if ss not in tmp_s:\n",
    "                tmp_s = tmp_s + ss\n",
    "            else:\n",
    "                tmp_s = ss\n",
    "                cn += 1\n",
    "        if tmp_s != \"\":\n",
    "            return cn + 1\n",
    "        else:\n",
    "            return cn"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "from typing import List\n",
    "import collections\n",
    "\n",
    "from collections import Counter\n",
    "class Solution:\n",
    "    def partitionString(self, s: str) -> int:\n",
    "        if not s:\n",
    "            return 0\n",
    "\n",
    "        sub_s = set()\n",
    "\n",
    "        cnt = 1\n",
    "        for char in s:\n",
    "            if char not in sub_s:\n",
    "                sub_s.add(char)\n",
    "                print(sub_s, cnt)\n",
    "            else:\n",
    "                cnt += 1\n",
    "                sub_s = set()\n",
    "                sub_s.add(char)\n",
    "        return cnt\n"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "from typing import List\n",
    "import collections\n",
    "\n",
    "class Solution:\n",
    "    def partitionString(self, s: str) -> int:\n",
    "        my_dict = {}\n",
    "        count = 0\n",
    "        start = 0\n",
    "        for index, char in enumerate(s):\n",
    "            if char not in my_dict:\n",
    "                my_dict[char] = index\n",
    "            elif start > my_dict[char]:\n",
    "                my_dict[char] = index\n",
    "            else:\n",
    "                \n",
    "                count += 1\n",
    "                start = index\n",
    "                my_dict[char] = index\n",
    "                print(start)\n",
    "        if start <= len(s) - 1:\n",
    "            # results.append(s[start:])\n",
    "            count += 1\n",
    "        return count"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "from typing import List\n",
    "import collections\n",
    "\n",
    "class Solution:\n",
    "    def partitionString(self, s: str) -> int:\n",
    "        start,ans = 0,0\n",
    "        arr = list(s)\n",
    "        for i in range(1,len(arr)):\n",
    "            if arr[i] in arr[start:i]:\n",
    "                ans += 1\n",
    "                start = i\n",
    "                # print(i)\n",
    "        return ans+1\n",
    "            \n"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "from typing import List\n",
    "import collections\n",
    "\n",
    "class Solution:\n",
    "    def partitionString(self, s: str) -> int:\n",
    "        s = list(s)\n",
    "        base = 0\n",
    "        ans = 1\n",
    "        for i in range(1,len(s)):\n",
    "            if s[i] in s[base:i]:\n",
    "                ans += 1\n",
    "                base = i\n",
    "        return ans\n",
    "\n"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "from typing import List\n",
    "import collections\n",
    "\n",
    "class Solution:\n",
    "    def partitionString(self, s: str) -> int:\n",
    "        res = []\n",
    "        tmp = \"\"\n",
    "        for i in s:\n",
    "            if i not in tmp:\n",
    "                tmp+=i\n",
    "            else:\n",
    "                res.append(tmp)\n",
    "                tmp=i\n",
    "        res.append(tmp)\n",
    "        return(len(res))\n",
    "#        return(max(s.count(x) for x in s))"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "from typing import List\n",
    "import collections\n",
    "\n",
    "class Solution:\n",
    "    def partitionString(self, s: str) -> int:\n",
    "        lst = ['']\n",
    "        l = len(s)\n",
    "        cnt = 0\n",
    "        for i in range(l):\n",
    "            if s[i] not in lst[cnt]:\n",
    "                lst[cnt] += s[i]\n",
    "            else:\n",
    "                cnt +=1\n",
    "                lst.append(s[i])\n",
    "        return len(lst)"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "from typing import List\n",
    "import collections\n",
    "\n",
    "class Solution:\n",
    "    def partitionString(self, s: str) -> int:\n",
    "        lst = ['']\n",
    "        l = len(s)\n",
    "        cnt = 0\n",
    "        for i in range(l):\n",
    "            if s[i] not in lst[cnt]:\n",
    "                lst[cnt] += s[i]\n",
    "            else:\n",
    "                cnt +=1\n",
    "                lst.append(s[i])\n",
    "        return len(lst)"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "from typing import List\n",
    "import collections\n",
    "\n",
    "class Solution:\n",
    "    def minCost(self, houses: List[int], cost: List[List[int]], m: int, n: int, target: int) -> int:\n",
    "        # 排除一些特殊情况\n",
    "        if m < target:\n",
    "            return -1\n",
    "        elif m == 1 and target == 1:\n",
    "            if houses[0] != 0:\n",
    "                return 0\n",
    "            else:\n",
    "                return cost[0][0]\n",
    "\n",
    "        # 3维的动态规划\n",
    "        INF = 10 ** 9\n",
    "\n",
    "        # 初始化dp数组\n",
    "        dp = [[[INF for _ in range(target + 1)] for _ in range(n + 1)] for _ in range(m + 1)]\n",
    "        # 对某些数值进一步初始化,即 房屋编号为0且分区为0的dp——初始化易导致出错\n",
    "        for j in range(n + 1):\n",
    "            dp[0][j][0] = 0\n",
    "\n",
    "        # 开始dp\n",
    "        # 首先遍历房子序号\n",
    "        for i in range(m + 1):\n",
    "            color = houses[i - 1]\n",
    "            # 接着遍历决策颜色与分区\n",
    "            for j in range(1, n + 1):\n",
    "                partitionEnd = min(i + 1, target + 1)\n",
    "                for k in range(1, partitionEnd):\n",
    "                    # 如果可以涂色,从不新增分区与新增分区中找到min值,再加上cost\n",
    "                    if color == 0:\n",
    "                        # 1、不新增分区\n",
    "                        tmp1 = dp[i - 1][j][k]\n",
    "                        \n",
    "                        #2、新增分区\n",
    "                        tmp2 = INF\n",
    "                        for p in range(1, n + 1):\n",
    "                            # 这个地方易错,等式右侧是j而不是color！！！！\n",
    "                            if p != j:\n",
    "                                tmp2 = min(tmp2, dp[i - 1][p][k - 1])\n",
    "                        \n",
    "                        # 当前取值即为\n",
    "                        dp[i][j][k] = min(tmp1, tmp2) + cost[i - 1][j - 1]\n",
    "                        \n",
    "                    # 如果不可以涂色\n",
    "                    else:\n",
    "                        # 如果决策的颜色不同于当前颜色\n",
    "                        if j != color:\n",
    "                            dp[i][j][k] = INF\n",
    "                        else:\n",
    "                            # 1、不新增分区\n",
    "                            tmp1 = dp[i - 1][j][k]\n",
    "                            \n",
    "                            #2、新增分区\n",
    "                            tmp2 = INF\n",
    "                            for p in range(1, n + 1):\n",
    "                            # 这个地方易错,等式右侧是j而不是color！！！！\n",
    "                                if p != j:\n",
    "                                    tmp2 = min(tmp2, dp[i - 1][p][k - 1])\n",
    "                            \n",
    "                            # 当前取值即为\n",
    "                            dp[i][j][k] = min(tmp1, tmp2)\n",
    "        # print(dp)\n",
    "\n",
    "        # 得到结果\n",
    "        ans = INF\n",
    "        for j in range(1, n + 1):\n",
    "            ans = min(ans, dp[m][j][target])\n",
    "        if ans != INF:\n",
    "            return ans\n",
    "        else:\n",
    "            return -1\n"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "from typing import List\n",
    "import collections\n",
    "\n",
    "class Solution:\n",
    "    def minCut(self, s: str) -> int:\n",
    "        # import functools\n",
    "        n=len(s)\n",
    "        # dp\n",
    "        # dp[i] define as partition when i==rightmost\n",
    "        # loop last subarray from i <--to left, \n",
    "        # when lastsub is palindrome, refer to dp[i-len(sub)]+1\n",
    "        dp=[float('inf') for i in range(n)]\n",
    "        dp[0]=0#one letter is palindrome, no need cut\n",
    "        # @functools.lru_cache(maxsize=None)\n",
    "        # def is_palindrome(left,right):#check subarray of s\n",
    "        #     if left>=right:return True\n",
    "        #     if s[left]!=s[right]:return False\n",
    "        #     return is_palindrome(left+1,right-1)\n",
    "\n",
    "        # update: try pre-calculate is_palindrome\n",
    "        is_palindrome=[[None for left in range(n)]for right in range(n)]\n",
    "        for right_left in range(n):#right-left\n",
    "            for left in range(0,n-right_left):\n",
    "                right=left+right_left\n",
    "                if left==right:is_palindrome[left][right]=True;continue\n",
    "                if s[left]!=s[right]:is_palindrome[left][right]=False\n",
    "                elif right-left+1==2:#if len==2\n",
    "                    is_palindrome[left][right]=True\n",
    "                else:#refer to left+1, right-1\n",
    "                    is_palindrome[left][right]=is_palindrome[left+1][right-1]\n",
    "                \n",
    "        for i in range(1,n):\n",
    "            if is_palindrome[0][i]:#if all is palindrome\n",
    "                dp[i]=0;continue\n",
    "            for len_subarray in range(1,i+1):#check each palindrome sub\n",
    "                # subarray=i-len_subarray,i\n",
    "                if is_palindrome[i-len_subarray+1][i]:\n",
    "                    dp[i]=min(dp[i],dp[i-len_subarray]+1)\n",
    "        return dp[-1]"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "from typing import List\n",
    "import collections\n",
    "\n",
    "class Solution:\n",
    "    def minCut(self, s: str) -> int:\n",
    "        n = len(s)\n",
    "        dp = [[True] * n for _ in range(n)]\n",
    "        # dp[i][j] denotes the where the subarray s[i: j+1] is Palindrome\n",
    "\n",
    "        for i in range(n-1, -1, -1):\n",
    "            for j in range(i+1, n):\n",
    "                dp[i][j] = (s[i] == s[j]) and dp[i+1][j-1]\n",
    "        \n",
    "        p_dp = [float('inf')] * n \n",
    "        # p_dp[i] denotes the min partition of palindrome substring for s[:i+1]\n",
    "\n",
    "        for i in range(n):\n",
    "            if dp[0][i]:\n",
    "                p_dp[i] = 0\n",
    "\n",
    "            for j in range(i):\n",
    "                if dp[j+1][i]:\n",
    "                    p_dp[i] = min(p_dp[i], p_dp[j] + 1)\n",
    "\n",
    "        return p_dp[-1]"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "from typing import List\n",
    "import collections\n",
    "\n",
    "class Solution:\n",
    "    def palindromePartition(self, s: str, k: int) -> int:\n",
    "        @lru_cache(None)\n",
    "        def count(beg, end):\n",
    "            if beg >= end:\n",
    "                return 0\n",
    "            else:\n",
    "                return (s[beg] != s[end]) + count(beg+1, end-1)\n",
    "\n",
    "        @lru_cache(None)\n",
    "        def partition(i, k):\n",
    "            if k == 1:\n",
    "                return count(0,i)\n",
    "\n",
    "            return min(partition(j, k-1) + count(j+1, i) for j in range(k-2, i))\n",
    "\n",
    "        return partition(len(s)-1, k)\n",
    "           \n",
    "        "
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "from typing import List\n",
    "import collections\n",
    "\n",
    "class Solution:\n",
    "    def palindromePartition(self, s: str, k: int) -> int:\n",
    "        @lru_cache(None)\n",
    "        def count(beg, end):\n",
    "            if beg >= end:\n",
    "                return 0\n",
    "            else:\n",
    "                return (s[beg] != s[end]) + count(beg+1, end-1)\n",
    "\n",
    "        @lru_cache(None)\n",
    "        def partition(i, k):\n",
    "            if k == 1:\n",
    "                return count(0,i)\n",
    "\n",
    "            return min(partition(j, k-1) + count(j+1, i) for j in range(k-2, i))\n",
    "\n",
    "        return partition(len(s)-1, k)\n",
    "           \n",
    "        "
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "from typing import List\n",
    "import collections\n",
    "\n",
    "class Manacher:\n",
    "    def __init__(self, string=''):\n",
    "        self.string = string\n",
    "\n",
    "    def add_char(self):\n",
    "        add_string = '^'\n",
    "        for char in self.string:\n",
    "            add_string += '@' + char\n",
    "        add_string += '@*'\n",
    "        return add_string\n",
    "    \n",
    "    def get_p(self): \n",
    "        self.add_string = self.add_char()\n",
    "        self.P = [0] * len(self.add_string)\n",
    "        R, mid = 0, 0\n",
    "        for i in range(1, len(self.add_string)-1):\n",
    "            self.P[i] = min(self.P[mid*2-i], R-i) if R > i else 0\n",
    "            while self.add_string[i+1+self.P[i]] == self.add_string[i-1-self.P[i]]:\n",
    "                self.P[i] +=1\n",
    "            if i + self.P[i] > R:\n",
    "                R = i + self.P[i]\n",
    "                mid = i\n",
    "        return self.P\n",
    "    \n",
    "    def check_partition_s(self, l, r): # 判断在串S的区间[l,r]的子串是否为回文串。\n",
    "        l, r = l * 2 + 2, r * 2 + 2\n",
    "        mid = (l + r) // 2\n",
    "        return self.P[mid] > r - mid\n",
    "    \n",
    "\n",
    "class Solution:\n",
    "    def checkPartitioning(self, s: str) -> bool:\n",
    "        manacher = Manacher(s)\n",
    "        manacher.get_p()\n",
    "        n = len(s)\n",
    "        pre, suf = [], []\n",
    "        pre_vis = [0] * n \n",
    "        suf_vis = [0] * n\n",
    "        for i in range(0, n):\n",
    "            if manacher.check_partition_s(0, n-1-i):\n",
    "                pre.append(n-i-1)\n",
    "                pre_vis[n-i-1] = 1\n",
    "            if manacher.check_partition_s(i, n-1):\n",
    "                suf.append(i)\n",
    "                suf_vis[i] = 1\n",
    "\n",
    "        suf_n, cnt = len(suf), 0\n",
    "        for i in range(n):\n",
    "            if pre_vis[i]:\n",
    "                while cnt < suf_n and suf[cnt] < i + 2:\n",
    "                    cnt +=1\n",
    "                if cnt < suf_n and manacher.check_partition_s(i+1, suf[cnt]-1):\n",
    "                    return True\n",
    "        \n",
    "        # print(pre, suf, pre_vis, suf_vis)\n",
    "        pre_n, cnt = len(pre), 0\n",
    "        for i in range(n-1, 0, -1):\n",
    "            if suf_vis[i]:\n",
    "                while cnt < pre_n and pre[cnt] + 2 > i:\n",
    "                    cnt +=1\n",
    "                if cnt < pre_n and manacher.check_partition_s(pre[cnt]+1, i-1):\n",
    "                    return True\n",
    "        return False"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "from typing import List\n",
    "import collections\n",
    "\n",
    "class Manacher:\n",
    "    def __init__(self, string=''):\n",
    "        self.string = string\n",
    "\n",
    "    def add_char(self):\n",
    "        \"\"\"\n",
    "        对字符串预处理填充'#'，使得字符串长度强行满足奇数对称。\n",
    "        同时头尾插入一对不匹配字符，添加P数组计算的边界情况。\n",
    "        \"\"\"\n",
    "        add_string = '^'\n",
    "        for char in self.string:\n",
    "            add_string += '@' + char\n",
    "        add_string += '@*'\n",
    "        return add_string\n",
    "    \n",
    "    def get_p(self): # Manacher算法核心，利用对称性中心扩展O(n)计算P数组\n",
    "        self.add_string = self.add_char()\n",
    "        self.P = [0] * len(self.add_string)\n",
    "        R, mid = 0, 0\n",
    "        for i in range(1, len(self.add_string)-1):\n",
    "            self.P[i] = min(self.P[mid*2-i], R-i) if R > i else 0\n",
    "            while self.add_string[i+1+self.P[i]] == self.add_string[i-1-self.P[i]]:\n",
    "                self.P[i] +=1\n",
    "            if i + self.P[i] > R:\n",
    "                R = i + self.P[i]\n",
    "                mid = i    \n",
    "        return self.P\n",
    "    \n",
    "    def max_palindrome(self):\n",
    "        \"\"\"\n",
    "        利用manacher已计算好的P数组，输出最长的回文子串。可以直接解决 Leetcode 5. 最长回文子串\n",
    "        \"\"\"\n",
    "        self.get_p()\n",
    "        max_len, max_index = 0, 0\n",
    "        for index, value in enumerate(self.P):\n",
    "            if value > max_len:\n",
    "                max_len, max_index = value, index\n",
    "        start_index = (max_index - max_len) // 2\n",
    "        return self.string[start_index: start_index+max_len]\n",
    "\n",
    "    def check_partition_s(self, l, r): # 判断在串S的区间[l,r]的子串是否为回文串。\n",
    "        l, r = l * 2 + 2, r * 2 + 2\n",
    "        mid = (l + r) // 2\n",
    "        return self.P[mid] > r - mid\n",
    "        \n",
    "    def check_partition_p(self, l, r): # 判断在数组P的区间[l,r]内是否为回文串。\n",
    "        mid = (l + r) // 2\n",
    "        return self.P[mid] > r - mid\n",
    "\n",
    "class Solution:\n",
    "    def checkPartitioning(self, s: str) -> bool:\n",
    "        manacher = Manacher(s)\n",
    "        manacher.get_p()\n",
    "        n = len(s)\n",
    "        pre, suf = [], []\n",
    "        pre_vis, suf_vis = [0] * n, [0] * n\n",
    "        for i in range(0, n):\n",
    "            if manacher.check_partition_s(0, n-1-i):\n",
    "                pre.append(n-i-1)\n",
    "                pre_vis[n-i-1] = 1\n",
    "            if manacher.check_partition_s(i, n-1):\n",
    "                suf.append(i)\n",
    "                suf_vis[i] = 1\n",
    "\n",
    "        suf_n, cnt = len(suf), 0\n",
    "        for i in range(n):\n",
    "            if pre_vis[i]:\n",
    "                while cnt < suf_n and suf[cnt] < i + 2:\n",
    "                    cnt +=1\n",
    "                if cnt < suf_n and manacher.check_partition_s(i+1, suf[cnt]-1):\n",
    "                    return True\n",
    "        pre_n, cnt = len(pre), 0\n",
    "        for i in range(n-1, 0, -1):\n",
    "            if suf_vis[i]:\n",
    "                while cnt < pre_n and pre[cnt] + 2 > i:\n",
    "                    cnt +=1\n",
    "                if cnt < pre_n and manacher.check_partition_s(pre[cnt]+1, i-1):\n",
    "                    return True\n",
    "        return False"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "from typing import List\n",
    "import collections\n",
    "\n",
    "class Solution:\n",
    "    def partition(self, s: str) -> List[List[str]]:\n",
    "        n = len(s)\n",
    "        def isPalindrome(i, j):\n",
    "            while i < j: \n",
    "                if s[i] != s[j]:\n",
    "                    return False\n",
    "                i += 1\n",
    "                j -= 1\n",
    "            \n",
    "            return True\n",
    "        \n",
    "        @cache\n",
    "        def recur(i):\n",
    "            if i == n:\n",
    "                return [[]] \n",
    "            ans = []\n",
    "            for j in range(i, n):\n",
    "                if isPalindrome(i, j):\n",
    "                    ans += [[s[i:j+1]] + x for x in recur(j + 1)]\n",
    "            return ans\n",
    "        return recur(0)\n",
    "        "
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "from typing import List\n",
    "import collections\n",
    "\n",
    "import copy\n",
    "\n",
    "\n",
    "class Solution:\n",
    "    def partition(self, s):\n",
    "        \"\"\"\n",
    "        :type s: str\n",
    "        :rtype: List[List[str]]\n",
    "        \"\"\"\n",
    "        if not s:\n",
    "            return []\n",
    "        res = []\n",
    "        dp = []\n",
    "        for _ in range(len(s)):\n",
    "            dp.append([False] * len(s))\n",
    "        self.helper(s, 0, res, [], dp)\n",
    "        return res\n",
    "\n",
    "    def helper(self, s, cur, res, temp, dp):\n",
    "        if cur == len(s):\n",
    "            res.append(copy.deepcopy(temp))\n",
    "            return\n",
    "        for i in range(cur, len(s)):\n",
    "            if self.is_plaindrome(cur, i, dp, s):\n",
    "                dp[cur][i] = True\n",
    "                temp.append(s[cur:i + 1])\n",
    "                self.helper(s, i + 1, res, temp, dp)\n",
    "                temp.pop()\n",
    "\n",
    "    def is_plaindrome(self, i, j, dp, s):\n",
    "        if s[i] == s[j]:\n",
    "            if i == j or j == i + 1 or dp[i + 1][j - 1]:\n",
    "                return True\n",
    "        return False"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "from typing import List\n",
    "import collections\n",
    "\n",
    "import copy\n",
    "class Solution:\n",
    "    def partition(self, s: str) -> List[List[str]]:\n",
    "        if not s:\n",
    "            return []\n",
    "        temp = []\n",
    "        res = []\n",
    "        self.DFS(s, temp, res)\n",
    "        return res\n",
    "        \n",
    "    def DFS(self, s, temp, res):\n",
    "        if not s:\n",
    "            res.append(copy.copy(temp))\n",
    "        for length in range(1, len(s)+1):\n",
    "            if(self.isPalindrome(s[:length])):\n",
    "                temp.append(s[:length])\n",
    "                self.DFS(s[length:], temp, res)\n",
    "                temp.pop()\n",
    "    \n",
    "    def isPalindrome(self, s: str) -> bool:\n",
    "        if not s:\n",
    "            return True\n",
    "        temp = ''\n",
    "        s = s.lower()\n",
    "        for c in s:\n",
    "            if c.isalnum():\n",
    "                temp += c\n",
    "        l = len(temp)\n",
    "        if not temp:\n",
    "            return True\n",
    "        \n",
    "        for i in range(0, l):\n",
    "            if temp[i] != temp[l-1-i]:\n",
    "                return False\n",
    "        \n",
    "        return True"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "from typing import List\n",
    "import collections\n",
    "\n",
    "class Solution:\n",
    "    def ispar(self,s):\n",
    "        l=len(s)\n",
    "        for i in range(l//2):\n",
    "            if s[i]!=s[l-1-i]:\n",
    "                return 0\n",
    "        return 1\n",
    "    \n",
    "    def func(self,res,tmp,start,n,s):\n",
    "        if start>=n:\n",
    "            res.append(tmp[:])\n",
    "            return\n",
    "        for i in range(start,n):\n",
    "            if self.ispar(s[start:i+1])==1:\n",
    "                tmp.append(s[start:i+1])\n",
    "                self.func(res,tmp,i+1,n,s)\n",
    "                del tmp[-1]\n",
    "        return\n",
    "    \n",
    "    def partition(self, s: str) -> List[List[str]]:\n",
    "        l=len(s)\n",
    "        res=[]\n",
    "        self.func(res,[],0,l,s)\n",
    "        return res"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "from typing import List\n",
    "import collections\n",
    "\n",
    "class Solution:\n",
    "    def partition(self, s):\n",
    "        \"\"\"\n",
    "        :type s: str\n",
    "        :rtype: List[List[str]]\n",
    "        \"\"\"\n",
    "        if len(s) == 0:\n",
    "            return []\n",
    "        par_list = [[] for col in range(len(s))]\n",
    "        return self.find_pal_par_list(s, len(s) - 1, par_list)\n",
    "\n",
    "    def find_pal_par_list(self, s, endIndex, par_list):\n",
    "        if endIndex == -1:\n",
    "            return [[]]\n",
    "        if len(par_list[endIndex]) != 0:\n",
    "            return par_list[endIndex]\n",
    "        i = 0\n",
    "        while endIndex - i >= 0:\n",
    "            if self.isPalindrome(s, endIndex - i, endIndex):\n",
    "                last = self.find_pal_par_list(s, endIndex - i - 1, par_list)\n",
    "                pal = s[endIndex - i: endIndex + 1]\n",
    "                for each_par in last:\n",
    "                    par_list[endIndex].insert(0, each_par + [pal])\n",
    "            i += 1\n",
    "        return par_list[endIndex]\n",
    "\n",
    "    def isPalindrome(self, s, i, j):\n",
    "        while i < j:\n",
    "            if s[i] != s[j]:\n",
    "                return False\n",
    "            i += 1\n",
    "            j -= 1\n",
    "        return True"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "from typing import List\n",
    "import collections\n",
    "\n",
    "class Solution:\n",
    "    def partition(self, s):\n",
    "        \"\"\"\n",
    "        :type s: str\n",
    "        :rtype: List[List[str]]\n",
    "        \"\"\"\n",
    "        dp = [[] for _ in range(len(s)+1)]\n",
    "        for i in range(1, len(s)+1):\n",
    "            for j in range(i):\n",
    "                if self.isPalindrome(s[j:i]):\n",
    "                    if len(dp[j]) > 0:\n",
    "                        for l in dp[j]:\n",
    "                            dp[i].append(l+[s[j:i]])\n",
    "                    else:\n",
    "                        dp[i].append([s[j:i]])\n",
    "        \n",
    "        return dp[-1]\n",
    "                        \n",
    "    def isPalindrome(self,s):\n",
    "        for i in range(len(s)>>1):\n",
    "            if s[i] != s[len(s)-1-i]:\n",
    "                return False \n",
    "        return True\n"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "from typing import List\n",
    "import collections\n",
    "\n",
    "class Solution:\n",
    "    def partition(self, s):\n",
    "        \"\"\"\n",
    "        :type s: str\n",
    "        :rtype: List[List[str]]\n",
    "        \"\"\"\n",
    "        \n",
    "        length = len(s)\n",
    "        palindrom = []\n",
    "        for i in range(0, length):\n",
    "            row = []\n",
    "            for j in range(0, length):\n",
    "                if i == j:\n",
    "                    row.append(1)\n",
    "                else:\n",
    "                    row.append(0)\n",
    "            palindrom.append(row)\n",
    "            \n",
    "        for j in range(1, length):\n",
    "            for i in range(1, j):\n",
    "                if palindrom[i][j - 1] == 1 and s[i - 1] == s[j]:\n",
    "                    palindrom[i - 1][j] = 1\n",
    "            if s[j - 1] == s[j]:\n",
    "                palindrom[j - 1][j] = 1\n",
    "                    \n",
    "        # for i in range(0, length):\n",
    "        #     for j in range(i, length):\n",
    "        #         if palindrom[i][j] == 1:\n",
    "        #             print(s[i:j+1])\n",
    "        \n",
    "        partitionDict = {}\n",
    "        for i in range(length - 1, -1, -1):\n",
    "            subPartitions = []\n",
    "            for j in range(i, length):\n",
    "                if palindrom[i][j] == 1:\n",
    "                    if j == length - 1:\n",
    "                        subPartitions.append([s[i:j + 1]])\n",
    "                    else:\n",
    "                        for subPartition in partitionDict[str(j + 1) + ',' + str(length - 1)]:\n",
    "                            newSubPartition = subPartition.copy()\n",
    "                            newSubPartition.insert(0, s[i:j + 1])\n",
    "                            subPartitions.append(newSubPartition)\n",
    "            partitionDict[str(i) + ',' + str(length - 1)] = subPartitions\n",
    "            # print(str(i) + ',' + str(length - 1) + \":\")\n",
    "            # print(subPartitions)\n",
    "        \n",
    "        return partitionDict['0,' + str(length - 1)]\n",
    "        "
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "from typing import List\n",
    "import collections\n",
    "\n",
    "class Solution:\n",
    "    def partition(self, s: str) -> List[List[str]]:\n",
    "        if not s:\n",
    "            return []\n",
    "        result = []\n",
    "        self.dfs(s, result, [])\n",
    "        return result\n",
    "\n",
    "    def dfs(self, s, result, stringlist):\n",
    "        if len(s) == 0:\n",
    "            result.append(list(stringlist))\n",
    "            return \n",
    "        for i in range(1, len(s) + 1):\n",
    "            if s[:i] == s[:i][::-1]:\n",
    "                self.dfs(s[i:], result, stringlist + [s[:i]])\n",
    "        "
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "from typing import List\n",
    "import collections\n",
    "\n",
    "#回溯\n",
    "#Time:O(n²)\n",
    "#Space:O(n)\n",
    "class Solution:\n",
    "    def partition(self, s: str) -> List[List[str]]:\n",
    "        if len(s)==0:\n",
    "            return [[]]\n",
    "        if len(s)==1:\n",
    "            return [[s]]\n",
    "        tmp = []\n",
    "        for i in range(1,len(s)+1):\n",
    "            left = s[:i]\n",
    "            right = s[i:]\n",
    "            if left == left[::-1]:\n",
    "                right = self.partition(right)\n",
    "                for i in range(len(right)):\n",
    "                    tmp.append([left]+right[i])\n",
    "        return tmp"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "from typing import List\n",
    "import collections\n",
    "\n",
    "class Solution:\n",
    "    def partition(self, s: str) -> List[List[str]]:\n",
    "\n",
    "        res = []\n",
    "\n",
    "        def backtrack(s,tmp):\n",
    "            if not s:\n",
    "                res.append(tmp)\n",
    "            else:\n",
    "                for i in range(1,len(s)+1):\n",
    "                    if s[:i] == s[:i][::-1]:\n",
    "                        backtrack(s[i:],tmp+[s[:i]])\n",
    "            \n",
    "        backtrack(s,[])\n",
    "        return res"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "from typing import List\n",
    "import collections\n",
    "\n",
    "class Solution:\n",
    "    def partition(self, s: str) -> List[List[str]]:\n",
    "        def backtrace(start):\n",
    "            if start == n:\n",
    "                results.append(result[:])\n",
    "            else:\n",
    "                # 此处需要增加一个回文判断的逻辑\n",
    "                # 但是整体框架不用变动\n",
    "                for i in range(start, n):\n",
    "                    substr = s[start:i + 1]\n",
    "                    if substr == substr[::-1]:\n",
    "                        result.append(substr)\n",
    "                        backtrace(i + 1)\n",
    "                        result.pop()\n",
    "        n = len(s)\n",
    "        results = []\n",
    "        result = []\n",
    "\n",
    "        backtrace(0)\n",
    "\n",
    "        return results\n",
    "\n"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "from typing import List\n",
    "import collections\n",
    "\n",
    "class Solution:\n",
    "    def partition(self, s: str) -> List[List[str]]:\n",
    "        def backtrace(start):\n",
    "            if start == n:\n",
    "                results.append(result[:])\n",
    "            else:\n",
    "                for i in range(start, n):\n",
    "                    substr = s[start:i + 1]\n",
    "                    if substr == substr[::-1]:\n",
    "                        result.append(substr)\n",
    "                        backtrace(i + 1)\n",
    "                        result.pop()\n",
    "\n",
    "        n = len(s)\n",
    "        results = []\n",
    "        result = []\n",
    "\n",
    "        backtrace(0)\n",
    "\n",
    "        return results\n",
    "\n"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "from typing import List\n",
    "import collections\n",
    "\n",
    "class Solution:\n",
    "    def partition(self, s: str) -> List[List[str]]:\n",
    "        # ans = []\n",
    "        # def recur_help(s,begin=0,split=[]):\n",
    "        #     if begin == len(s):\n",
    "        #         ans.append(split[:])\n",
    "        #     # else:\n",
    "        #     for i in range(begin+1,len(s)+1):\n",
    "        #         if self.isPalindrome(s[begin:i]):\n",
    "        #             split.append(s[begin:i])\n",
    "        #             recur_help(s,begin=i,split=split)\n",
    "        #             split.pop()\n",
    "        # recur_help(s)\n",
    "        # return ans\n",
    "\n",
    "        # 动态规划\n",
    "        # 若已知s[:1],s[:2],...,s[:len(s)-1]的分割方案，\n",
    "        # 若s[j:len(s)]是回文串，则s[:j]的分割方案加上s[j:len(s)]成为s的一种分割方案\n",
    "        ans = [[[s[0]]]]\n",
    "        for i in range(2,len(s)+1):\n",
    "            ans.append([])\n",
    "            for j in range(i-1, -1, -1):\n",
    "                if self.isPalindrome(s[j:i]):\n",
    "                    if j - 1 >= 0:\n",
    "                        for p in ans[j-1]:\n",
    "                            ans[i-1].append(p+[s[j:i]])\n",
    "                    else:\n",
    "                        ans[i-1].append([s[j:i]])\n",
    "        return ans[-1]\n",
    "    def isPalindrome(self,s):\n",
    "        left, right = 0, len(s) - 1\n",
    "        while left < right:\n",
    "            if s[left] != s[right]:\n",
    "                return False\n",
    "            left += 1\n",
    "            right -= 1\n",
    "        return True"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "from typing import List\n",
    "import collections\n",
    "\n",
    "class Solution:\n",
    "    def partition(self, s: str) -> List[List[str]]:\n",
    "        def isPa(s):\n",
    "            if s == \"\":\n",
    "                return True\n",
    "            else:\n",
    "                l = 0\n",
    "                r = len(s-1)\n",
    "                while l<=r:\n",
    "                    if s[l] != s[r]:\n",
    "                        return False\n",
    "                return True\n",
    "        \n",
    "        is_pa = [[False] * (len(s)+1) for _ in range(len(s))]\n",
    "\n",
    "        for i in range(1,len(s)+1):\n",
    "            for start in range(0, len(s)-i+1):\n",
    "                end = start + i\n",
    "                if i == 1:\n",
    "                    is_pa[start][end] = True\n",
    "                elif i == 2:\n",
    "                    is_pa[start][end] = s[start] == s[start+1]\n",
    "                else:\n",
    "                    is_pa[start][end] = is_pa[start+1][end-1] and s[start] == s[end-1]\n",
    "        \n",
    "        res = [[[]]]\n",
    "        for i in range(1, len(s)+1):\n",
    "            cur = []\n",
    "            for j in range(0, i):\n",
    "                #print(j)\n",
    "                #print(i, is_pa[j][i])\n",
    "                if is_pa[j][i]:\n",
    "                    #print(res[j])\n",
    "                    for item in res[j]:\n",
    "                        cur.append(item + [s[j:i]])\n",
    "            res.append(cur)\n",
    "        \n",
    "        return(res[-1])\n",
    "\n"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "from typing import List\n",
    "import collections\n",
    "\n",
    "class Solution:\n",
    "    def partition(self, s: str) -> List[List[str]]:\n",
    "        dp = [[] for _ in range(len(s) + 1)]\n",
    "        dp[-1] = [[]]\n",
    "        for i in range(len(s) - 1, -1, -1):\n",
    "            for j in range(i + 1, len(s) + 1):\n",
    "                if s[i:j] == s[i:j][::-1]:\n",
    "                    for each in dp[j]:\n",
    "                        dp[i].append([s[i:j]] + each)\n",
    "        return dp[0]"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "from typing import List\n",
    "import collections\n",
    "\n",
    "class Solution:\n",
    "    def __init__(self):\n",
    "        self.hw_map = dict()\n",
    "        self.seq_map = dict()\n",
    "\n",
    "    def partition(self, s: str) -> List[List[str]]:\n",
    "        \"\"\"\n",
    "        F(s, begin, end) = Huiwen(s, begin, begin + 1) * F(s, begin + 1, end) \n",
    "                         + Huiwen(s, begin, begin + 2) * F(s, begin + 1, end) \n",
    "                         ...\n",
    "                         + Huiwen(s, begin, begin) * 1 \n",
    "        \"\"\"\n",
    "        str_a = [x for x in s]\n",
    "        result = self.dfs_huiwen(s, 0, len(s))\n",
    "        return result\n",
    "\n",
    "    def dfs_huiwen(self, s, begin, end):\n",
    "        str_seq = s[begin: end]\n",
    "        if str_seq in self.seq_map:\n",
    "            return self.seq_map[str_seq]\n",
    "        t = end - begin\n",
    "        if t <= 0:\n",
    "            return [[]]\n",
    "        if t == 1:\n",
    "            return [[s[begin]]]\n",
    "        r = []\n",
    "        for i in  range(begin + 1 , end + 1):\n",
    "            first_s = s[begin: i]\n",
    "            if self.is_huiwen_str(first_s):\n",
    "                lr = self.dfs_huiwen(s, i, end)\n",
    "                if i >= end or lr:\n",
    "                    nr = []\n",
    "                    for sub in lr:\n",
    "                        nr.append([first_s] + sub)\n",
    "                    r.extend(nr)\n",
    "        self.seq_map[str_seq] = r\n",
    "        return r\n",
    "\n",
    "    def is_huiwen_str(self, s: str) -> bool:\n",
    "        n = len(s)\n",
    "        if n == 0:\n",
    "            return False\n",
    "        if n == 1:\n",
    "            return True\n",
    "        if s in self.hw_map:\n",
    "            return self.hw_map[s]\n",
    "        r = True\n",
    "        half = (int)(n / 2)\n",
    "        for i in range(half):\n",
    "            if s[i] != s[n - i - 1]:\n",
    "                r = False\n",
    "        return r\n"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "from typing import List\n",
    "import collections\n",
    "\n",
    "def isPalindrome(s: str) -> bool:\n",
    "    if len(s) <= 1:\n",
    "        return True\n",
    "    first = 0\n",
    "    second = len(s) - 1\n",
    "    while first < second:\n",
    "        while not s[first].isalnum() and first < second:\n",
    "            first += 1\n",
    "        while not s[second].isalnum() and first < second:\n",
    "            second -= 1\n",
    "        if s[first].lower() != s[second].lower():\n",
    "            return False\n",
    "        first += 1\n",
    "        second -= 1\n",
    "    return True\n",
    "\n",
    "class Solution:\n",
    "    def partition(self, s: str) -> List[List[str]]:\n",
    "        def helper(cur_str, path, result):\n",
    "            if len(cur_str) == 0:\n",
    "                if len(path) != 0:\n",
    "                    result.append(deepcopy(path))\n",
    "                return\n",
    "            for index in range(1, len(cur_str)+1):\n",
    "                prefix = cur_str[:index]\n",
    "                if prefix not in dp:\n",
    "                    dp[prefix] = isPalindrome(prefix)\n",
    "                if not dp[prefix]:\n",
    "                    continue\n",
    "                path.append(prefix)\n",
    "                helper(cur_str[index:], path, result)\n",
    "                path.pop()\n",
    "        if len(s) == 0:\n",
    "            return [[]]\n",
    "        if len(s) == 1:\n",
    "            return [[s]]\n",
    "        dp = dict()\n",
    "        path = []\n",
    "        result = []\n",
    "        helper(s, path, result)\n",
    "        return result"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "from typing import List\n",
    "import collections\n",
    "\n",
    "class Solution:\n",
    "    def partition(self, s: str) -> List[List[str]]:\n",
    "        def x(s):\n",
    "            n = len(s)\n",
    "            for i in range(n // 2):\n",
    "                if s[i] != s[n - 1 - i]:\n",
    "                    return False\n",
    "            return True\n",
    "        @lru_cache(None)\n",
    "        def f(s):\n",
    "            if len(s) == 0:\n",
    "                return []\n",
    "            elif len(s) == 1:\n",
    "                return [[s]]\n",
    "            else:\n",
    "                ans = []\n",
    "                for i in range(1, len(s)):\n",
    "                    if x(s[:i]):\n",
    "                        for k in f(s[i:]):\n",
    "                            ans.append([s[:i]] + k)\n",
    "                if x(s):\n",
    "                    ans.append([s])\n",
    "                return ans\n",
    "        return f(s)\n",
    "\n",
    "\n"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "from typing import List\n",
    "import collections\n",
    "\n",
    "class Solution:\n",
    "    def __init__(self):\n",
    "        self.hw_map = dict()\n",
    "        self.seq_map = dict()\n",
    "\n",
    "    def partition(self, s: str) -> List[List[str]]:\n",
    "        \"\"\"\n",
    "        F(s, begin, end) = Huiwen(s, begin, begin + 1) * F(s, begin + 1, end) \n",
    "                         + Huiwen(s, begin, begin + 2) * F(s, begin + 1, end) \n",
    "                         ...\n",
    "                         + Huiwen(s, begin, begin) * 1 \n",
    "        \"\"\"\n",
    "        str_a = [x for x in s]\n",
    "        result = self.dfs_huiwen(s, 0, len(s))\n",
    "        return result\n",
    "\n",
    "    def dfs_huiwen(self, s, begin, end):\n",
    "        if (begin, end) in self.seq_map:\n",
    "            return self.seq_map[(begin, end)]\n",
    "        t = end - begin\n",
    "        if t <= 0:\n",
    "            return [[]]\n",
    "        if t == 1:\n",
    "            return [[s[begin]]]\n",
    "        r = []\n",
    "        for i in  range(begin + 1 , end + 1):\n",
    "            first_s = s[begin: i]\n",
    "            if self.is_huiwen_str(first_s):\n",
    "                lr = self.dfs_huiwen(s, i, end)\n",
    "                if i >= end or lr:\n",
    "                    nr = []\n",
    "                    for sub in lr:\n",
    "                        nr.append([first_s] + sub)\n",
    "                    r.extend(nr)\n",
    "        self.seq_map[(begin,end)] = r\n",
    "        return r\n",
    "\n",
    "    def is_huiwen_str(self, s: str) -> bool:\n",
    "        n = len(s)\n",
    "        if n == 0:\n",
    "            return False\n",
    "        if n == 1:\n",
    "            return True\n",
    "        if s in self.hw_map:\n",
    "            return self.hw_map[s]\n",
    "        r = True\n",
    "        half = (int)(n / 2)\n",
    "        for i in range(half):\n",
    "            if s[i] != s[n - i - 1]:\n",
    "                r = False\n",
    "        self.hw_map[s] = r\n",
    "        return r\n"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "from typing import List\n",
    "import collections\n",
    "\n",
    "class Solution:\n",
    "    def partition(self, s: str) -> List[List[str]]:\n",
    "\n",
    "        huiwenMemo = {}\n",
    "        def check(i, j): # s[i:j] 是否是回文串\n",
    "            if (i,j) not in huiwenMemo:\n",
    "                if j - i <= 1: \n",
    "                    huiwenMemo[(i,j)] = True\n",
    "                else:\n",
    "                    huiwenMemo[(i,j)] =  check(i+1, j-1) if s[i]==s[j-1] else False\n",
    "            return huiwenMemo[(i,j)]\n",
    "        \n",
    "\n",
    "        n = len(s)\n",
    "        dpMemo = {}\n",
    "        def dp(i): # s[i:] 分割成的回文串\n",
    "            if i not in dpMemo:\n",
    "                res = []\n",
    "                for k in range(i, n): # i=[i,..,n-1]\n",
    "                    if k==i:\n",
    "                        if check(i, n): # k==i时，检查整个字符串是否是回文\n",
    "                            res.append([s[i:]])\n",
    "                    else:\n",
    "                        if check(i, k):\n",
    "                            res.extend([[s[i:k]]+each for each in dp(k)])\n",
    "                dpMemo[i] = res\n",
    "            return dpMemo[i]\n",
    "        \n",
    "        return dp(0)\n"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "from typing import List\n",
    "import collections\n",
    "\n",
    "from functools import lru_cache\n",
    "class Solution:\n",
    "    def partition(self, s: str) -> List[List[str]]:\n",
    "        @lru_cache(None)\n",
    "        def check(b, e):\n",
    "            if b == e:\n",
    "                return True\n",
    "            if b + 1 == e:\n",
    "                return s[b] == s[e]\n",
    "            return check(b+1, e-1) and s[b] == s[e]\n",
    "\n",
    "        @lru_cache(None)\n",
    "        def get(b, e):\n",
    "            if b == e:\n",
    "                return [[s[b]]]\n",
    "            if b > e:\n",
    "                return [[]]\n",
    "            ans = []\n",
    "            for i in range(b, e+1):\n",
    "                if check(b, i):\n",
    "                    for item in get(i+1, e):\n",
    "                        ans.append([s[b:i+1]] + item)\n",
    "            return ans\n",
    "        \n",
    "        if not s:\n",
    "            return []\n",
    "        return get(0, len(s)-1)"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "from typing import List\n",
    "import collections\n",
    "\n",
    "from functools import lru_cache\n",
    "\n",
    "\n",
    "class Solution(object):\n",
    "    def partition(self, s):\n",
    "        \"\"\"\n",
    "        :type s: str\n",
    "        :rtype: List[List[str]]\n",
    "        \"\"\"\n",
    "        @lru_cache(None)\n",
    "        def dfs(idx):\n",
    "            if idx >= lens:\n",
    "                return [[]]\n",
    "            cur = []\n",
    "            for i in range(idx, lens):\n",
    "                if is_para(idx, i):\n",
    "                    cur += [[s[idx: i + 1]] + x for x in dfs(i + 1)]\n",
    "            return cur\n",
    "\n",
    "        @lru_cache(None)\n",
    "        def is_para(i, j):\n",
    "            return True if i >= j else s[i] == s[j] and is_para(i + 1, j - 1)\n",
    "\n",
    "        lens = len(s)\n",
    "        return dfs(0)"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "from typing import List\n",
    "import collections\n",
    "\n",
    "class Solution:\n",
    "\n",
    "    def isPNum(self,s):\n",
    "        l = len(s)\n",
    "        if l == 1:\n",
    "            return True\n",
    "        left = 0\n",
    "        right = l-1\n",
    "        while left < right:\n",
    "            if s[left] != s[right]:\n",
    "                return False\n",
    "            left += 1\n",
    "            right -= 1\n",
    "        return True\n",
    "\n",
    "\n",
    "    def partition(self, s: str) -> List[List[str]]:\n",
    "\n",
    "        isPNum = {}\n",
    "        cache = {}\n",
    "        def dfs(targetStr):\n",
    "            l = len(targetStr)\n",
    "            if l == 0:\n",
    "                return [[]]\n",
    "            elif l == 1:\n",
    "                return [[targetStr]]\n",
    "            if targetStr in cache:\n",
    "                return cache[targetStr]\n",
    "            res = []\n",
    "            for i in range(1,l+1):\n",
    "                temp = targetStr[:i]\n",
    "                flag = False\n",
    "                if temp in isPNum:\n",
    "                    flag = isPNum[temp]\n",
    "                else:\n",
    "                    flag = self.isPNum(temp)\n",
    "                    isPNum[temp] = flag\n",
    "                if not flag:\n",
    "                    continue\n",
    "                rest = dfs(targetStr[i:])\n",
    "                for one in rest:\n",
    "                    res.append([temp] + one)\n",
    "            \n",
    "            cache[targetStr] = res\n",
    "            return res\n",
    "        return dfs(s)\n",
    "\n",
    "                \n",
    "                \n",
    "\n",
    "\n",
    "\n",
    "\n",
    "\n",
    "\n",
    "\n",
    "\n",
    "\n",
    "\n",
    "\n",
    "\n",
    "\n",
    "\n",
    "\n",
    "\n"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "from typing import List\n",
    "import collections\n",
    "\n",
    "class Solution:\n",
    "    @functools.lru_cache(10000) \n",
    "    def partition(self, s: str) -> List[List[str]]:\n",
    "        if len(s) == 1:\n",
    "            return [[s]]\n",
    "        result = []\n",
    "        for i in range(len(s)):\n",
    "            first = s[:i+1]\n",
    "            #print(first, s[i+1:])\n",
    "            if self.judge(first):\n",
    "                if i == len(s) - 1:\n",
    "                    result.append([first])\n",
    "                else:\n",
    "                    for res in self.partition(s[i+1:]):\n",
    "                        result.append([first] + res[:])\n",
    "        \n",
    "        return result\n",
    "                \n",
    "    @functools.lru_cache(10000)    \n",
    "    def judge(self, s):\n",
    "        for i in range(len(s) // 2):\n",
    "            if s[i] != s[len(s)-1-i]:\n",
    "                return False\n",
    "        \n",
    "        return True"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "from typing import List\n",
    "import collections\n",
    "\n",
    "class Solution:\n",
    "    \n",
    "    @lru_cache(None)\n",
    "    def isSym(self, s):\n",
    "        return s == s[::-1]\n",
    "\n",
    "    @lru_cache(None)\n",
    "    def partition(self, s: str) -> List[List[str]]:\n",
    "        size = len(s)\n",
    "        if size == 0: return [[]]\n",
    "        if size == 1: return [[s]]\n",
    "\n",
    "        res = []\n",
    "        for i in range(1, size+1):\n",
    "            if self.isSym(s[:i]):\n",
    "                sub_res = self.partition(s[i:])\n",
    "                for sub_r in sub_res:\n",
    "                    res.append([s[:i]] + sub_r)\n",
    "\n",
    "        return res\n",
    "\n",
    "\n",
    "\n"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "from typing import List\n",
    "import collections\n",
    "\n",
    "class Solution:\n",
    "    def partition(self, s: str) -> List[List[str]]:\n",
    "        rst = []\n",
    "        buildpartition(s, 0, len(s)-1, [], rst)\n",
    "        return rst\n",
    "    \n",
    "def buildpartition(s, l, r, tmp, rst):\n",
    "    if l > r:\n",
    "        rst.append(tmp[:])\n",
    "        return\n",
    "\n",
    "    if check(s[l:r+1]):\n",
    "        tmp.append(s[l:r+1])\n",
    "        buildpartition(s, r + 1, len(s) - 1, tmp, rst)\n",
    "        tmp.pop()\n",
    "\n",
    "    if r > l:\n",
    "        r -= 1\n",
    "        buildpartition(s, l, r, tmp, rst)\n",
    "        \n",
    "def check(s):\n",
    "    n = len(s)\n",
    "    if n < 2:\n",
    "        return True\n",
    "\n",
    "    l = 0\n",
    "    r = n - 1\n",
    "    while l <= r:\n",
    "        if s[l] != s[r]:\n",
    "            return False\n",
    "        l += 1\n",
    "        r -= 1\n",
    "\n",
    "    return True"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "from typing import List\n",
    "import collections\n",
    "\n",
    "class Solution:\n",
    "    def partition(self, s: str) -> List[List[str]]:\n",
    "        if not s:\n",
    "            return []\n",
    "        n = len(s)\n",
    "        if n == 0:\n",
    "            return []\n",
    "        if n == 1:\n",
    "            return [[s]]\n",
    "\n",
    "        res = []\n",
    "\n",
    "        # 判断字符串是不是回文子串\n",
    "        def is_paladrome(string):\n",
    "            length = len(string)\n",
    "            if length == 1:\n",
    "                return True\n",
    "\n",
    "            left = (length - 1) // 2\n",
    "            right = left + (length + 1) % 2\n",
    "            while 0 <= left and right <= length - 1:\n",
    "                if string[left] != string[right]:\n",
    "                    return False\n",
    "                left -= 1\n",
    "                right += 1\n",
    "            return True\n",
    "\n",
    "        # 可以提前用动态规划处理原始字符串，这样的话可以在O(1)的时间复杂度内判断一个子串是否为回文子串\n",
    "        dp = [[False for _ in range(n)] for _ in range(n)]\n",
    "        for right in range(n):\n",
    "            # left可以等于right，表示字符串长度为1个字符\n",
    "            for left in range(right + 1):\n",
    "                if s[left] == s[right] and (right - left <= 2 or dp[left + 1][right - 1]):\n",
    "                    dp[left][right] = True\n",
    "\n",
    "        for i in range(1, n + 1):\n",
    "            first = s[0:i]\n",
    "            if dp[0][i - 1]:\n",
    "                if i == n:\n",
    "                    res.append([first])\n",
    "                else:\n",
    "                    second = s[i:]\n",
    "                    for r in self.partition(second):\n",
    "                        res.append([first] + r)\n",
    "\n",
    "        # for j in range(1, n + 1):\n",
    "        #     first = s[0:j]\n",
    "        #     if is_paladrome(first):\n",
    "        #         if j == n:\n",
    "        #             res.append([first])\n",
    "        #         else:\n",
    "        #             second = s[j:]\n",
    "        #             for r in self.partition(second):\n",
    "        #                 res.append([first] + r)\n",
    "\n",
    "        return res"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "from typing import List\n",
    "import collections\n",
    "\n",
    "class Solution:\n",
    "    def __init__(self):\n",
    "        self.error = 0\n",
    "    def partition(self, s: str) -> List[List[str]]:\n",
    "        if not s:\n",
    "            self.error = 1\n",
    "            return []\n",
    "        l = len(s)\n",
    "        if l == 1:\n",
    "            return [[s]]\n",
    "        res = []\n",
    "        dp = [[0 for i in range(l)] for j in range(l)]\n",
    "        for i in range(l):\n",
    "            dp[i][i] = 1\n",
    "        for i in range(l-1,-1,-1):\n",
    "            for j in range(i+1, l):\n",
    "                if s[i] == s[j]:\n",
    "                    if i == j-1:\n",
    "                        dp[i][j] = 1\n",
    "                    else:\n",
    "                        dp[i][j] = dp[i+1][j-1]\n",
    "        for i in range(l):\n",
    "            if dp[0][i]:\n",
    "                for item in self.partition(s[i+1:]):\n",
    "                    res.append([s[:i+1]]+item)\n",
    "                if i > l-2:\n",
    "                    res.append([s[:i+1]])\n",
    "        return res"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "from typing import List\n",
    "import collections\n",
    "\n",
    "class Solution:\n",
    "    \n",
    "    all_path = []\n",
    "    path = []\n",
    "\n",
    "    def backtrace(self, s, start):\n",
    "        if start >= len(s):\n",
    "            self.all_path.append(self.path.copy())\n",
    "            return\n",
    "        \n",
    "        for i in range(start, len(s)+1):\n",
    "            sub_s = s[start:i]\n",
    "            print(start, i, s, sub_s)\n",
    "            if not sub_s:\n",
    "                continue\n",
    "            if sub_s == sub_s[::-1]:\n",
    "                self.path.append(sub_s)\n",
    "                self.backtrace(s, i)\n",
    "                self.path.pop()\n",
    "            \n",
    "\n",
    "    def partition(self, s: str) -> List[List[str]]:\n",
    "        self.all_path.clear()\n",
    "        self.backtrace(s, 0)\n",
    "        return self.all_path\n"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "from typing import List\n",
    "import collections\n",
    "\n",
    "class Solution:\n",
    "    \n",
    "    all_path = []\n",
    "    path = []\n",
    "\n",
    "    def backtrace(self, s, start):\n",
    "        if start >= len(s):\n",
    "            self.all_path.append(self.path.copy())\n",
    "            return\n",
    "        \n",
    "        for i in range(start, len(s)+1):\n",
    "            sub_s = s[start:i]\n",
    "            # print(start, i, s, sub_s)\n",
    "            if not sub_s:\n",
    "                continue\n",
    "            if sub_s == sub_s[::-1]:\n",
    "                self.path.append(sub_s)\n",
    "                self.backtrace(s, i)\n",
    "                self.path.pop()\n",
    "            \n",
    "\n",
    "    def partition(self, s: str) -> List[List[str]]:\n",
    "        self.all_path.clear()\n",
    "        self.backtrace(s, 0)\n",
    "        return self.all_path\n"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "from typing import List\n",
    "import collections\n",
    "\n",
    "class Solution:\n",
    "    res = []\n",
    "    def huiWen(self, c):\n",
    "        for i in range(int(len(c) / 2)):\n",
    "            if c[i] != c[len(c) -i-1]:\n",
    "                return False\n",
    "        return True\n",
    "\n",
    "    def generatePartition(self, s, start, cur):\n",
    "        if start == len(s):\n",
    "            print(cur)\n",
    "            self.res.append(cur.copy())\n",
    "            return\n",
    "        for i in range(start, len(s)):\n",
    "            tmp = s[start:i+1]\n",
    "            print(tmp)\n",
    "            if self.huiWen(tmp):\n",
    "                cur.append(tmp)\n",
    "                self.generatePartition(s, i+1, cur)\n",
    "                cur.pop()\n",
    "    \n",
    "    def partition(self, s: str) -> List[List[str]]:\n",
    "        self.res.clear()\n",
    "        cur = []\n",
    "        self.generatePartition(s, 0, cur)\n",
    "        return self.res\n"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "from typing import List\n",
    "import collections\n",
    "\n",
    "class Solution:\n",
    "    path = []\n",
    "    result = []\n",
    "    \n",
    "    def isParli(self, s):\n",
    "        return s == s[::-1]\n",
    "\n",
    "    def backtracking(self, s, start_idx):\n",
    "        if start_idx >= len(s):\n",
    "            self.result.append(self.path.copy())\n",
    "        for i in range(start_idx, len(s)):\n",
    "            cur_s = s[start_idx:i+1]\n",
    "            if self.isParli(cur_s):\n",
    "                self.path.append(cur_s)\n",
    "                self.backtracking(s, i + 1)\n",
    "                self.path.pop()\n",
    "            else:\n",
    "                continue\n",
    "\n",
    "    def partition(self, s: str) -> List[List[str]]:\n",
    "        self.path.clear()\n",
    "        self.result.clear()\n",
    "        self.backtracking(s, 0)\n",
    "        return self.result\n",
    "\n"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "from typing import List\n",
    "import collections\n",
    "\n",
    "class Solution:\n",
    "    path = []\n",
    "    result = []\n",
    "\n",
    "    def is_pardo(self, s):\n",
    "        return s == s[::-1]\n",
    "\n",
    "    def backtrack(self, s, start_idx):\n",
    "        if len(s) == start_idx:\n",
    "           self.result.append(self.path.copy())\n",
    "\n",
    "        for i in range(start_idx, len(s)):\n",
    "            cur = s[start_idx:i+1]\n",
    "            if self.is_pardo(cur):\n",
    "                self.path.append(cur)\n",
    "                self.backtrack(s, i+1)\n",
    "                self.path.pop()\n",
    "            else:\n",
    "                continue\n",
    "          \n",
    "\n",
    "\n",
    "    def partition(self, s: str) -> List[List[str]]:\n",
    "        self.path.clear()\n",
    "        self.result.clear()\n",
    "        self.backtrack(s, 0)\n",
    "        return self.result"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "from typing import List\n",
    "import collections\n",
    "\n",
    "class Solution:\n",
    "    res = []\n",
    "    def partition(self, s: str) -> List[List[str]]:\n",
    "        self.res.clear()\n",
    "        if not s:\n",
    "            return self.res\n",
    "        record = []\n",
    "        self.dfs(s, 0, record)\n",
    "        return self.res\n",
    "    \n",
    "    def dfs(self, s, index, record):\n",
    "        if index >= len(s):\n",
    "            #print(record)\n",
    "            self.res.append(record[:])\n",
    "            return\n",
    "        for i in range(index, len(s)):\n",
    "            if self.isPalindrome(s, index, i):\n",
    "                record.append(s[index:i+1])\n",
    "                #print(record)\n",
    "                self.dfs(s, i+1, record)\n",
    "                record.pop()\n",
    "        return\n",
    "    def isPalindrome(self, s, l, r):\n",
    "        if l > r:\n",
    "            return True\n",
    "        if s[l] == s[r]:\n",
    "            return self.isPalindrome(s, l+1, r-1)\n",
    "        else:\n",
    "            return False\n"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "from typing import List\n",
    "import collections\n",
    "\n",
    "class Solution:\n",
    "    res = []\n",
    "    path = []\n",
    "    def backtrack(self, s: str, start_index: int):\n",
    "        if start_index >= len(s):\n",
    "            self.res.append(self.path[:])\n",
    "            return\n",
    "        for i in range(start_index, len(s)):\n",
    "            if self.ispalindrome(s, start_index, i):\n",
    "                self.path.append(s[start_index: i+1])\n",
    "                self.backtrack(s, i + 1)\n",
    "                self.path.pop()\n",
    "\n",
    "    def ispalindrome(self, s: str, start: int, end: int):\n",
    "        i, j = start, end\n",
    "        while i < j:\n",
    "            if s[i] != s[j]:\n",
    "                return False\n",
    "            i += 1\n",
    "            j -= 1\n",
    "        return True\n",
    "\n",
    "    def partition(self, s: str) -> List[List[str]]:\n",
    "        self.res.clear()\n",
    "        self.path.clear()\n",
    "        self.backtrack(s, 0)\n",
    "        return self.res"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "from typing import List\n",
    "import collections\n",
    "\n",
    "class Solution:\n",
    "    def partition(self, s: str) -> List[List[str]]:\n",
    "        data = {}\n",
    "        for i in range(len(s)):\n",
    "            data[i] = [(i, s[i])]\n",
    "            for j in range(i + 1, len(s)):\n",
    "                start = i\n",
    "                stop = j\n",
    "                while start < stop:\n",
    "                    if s[start] == s[stop]:\n",
    "                        start += 1\n",
    "                        stop -= 1\n",
    "                    else:\n",
    "                        break\n",
    "                else:\n",
    "                    data[i].append((j, s[i:j+1]))\n",
    "\n",
    "        res = []\n",
    "        stack = [[i] for i in data[0]]\n",
    "        while len(stack):\n",
    "            e = stack.pop()\n",
    "            if e[-1][0] == len(s) - 1:\n",
    "                res.append([i[1] for i in e])\n",
    "            else:\n",
    "                for i in data[e[-1][0] + 1]:\n",
    "                    bak = e.copy()\n",
    "                    bak.append(i)\n",
    "                    stack.append(bak)\n",
    "        return res"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "from typing import List\n",
    "import collections\n",
    "\n",
    "class Solution:\n",
    "    def partition(self, s):\n",
    "            \"\"\"\n",
    "            :type s: str\n",
    "            :rtype: List[List[str]]\n",
    "            \"\"\"\n",
    "            r = []\n",
    "            stop = {} # string(char) to position\n",
    "            p = {}\n",
    "            mul = []\n",
    "            sl = len(s)\n",
    "            for i in range(sl):\n",
    "                stop[s[i]] = stop[s[i]] + [i] if s[i] in stop else [i]\n",
    "            for i in stop:\n",
    "                for c in range(len(stop[i])):\n",
    "                    cc = stop[i][c]\n",
    "                    for ci in range(c, len(stop[i])):\n",
    "                        cci = stop[i][ci]+1\n",
    "                        si = s[cc: cci]\n",
    "                        if self.ispalin(si):\n",
    "                            p[cc] = p[cc] + [(cci, si)] if cc in p else [(cci, si)]\n",
    "                    l = len(p[cc])\n",
    "                    if l > 1:\n",
    "                        mul += [(cc, l-1)]\n",
    "            if len(mul) == 0:\n",
    "                return [list(s)]\n",
    "            mul.sort()\n",
    "            mulinp = {}\n",
    "            for i in range(len(mul)):\n",
    "                mulinp[mul[i][0]] = i\n",
    "            sl -= 1\n",
    "            pre = []\n",
    "            pp = 0\n",
    "            path = [-1 for i in mul]\n",
    "            pind = -1\n",
    "            paths = [[]]\n",
    "            while path[0] < mul[0][1] or path[pind] < mul[pind][1]:\n",
    "                while pp <= sl:\n",
    "                    if pp not in mulinp:\n",
    "                        pre += [p[pp][0][1]]\n",
    "                        paths[-1] += [p[pp][0][1]]\n",
    "                        pp += 1\n",
    "                    else:\n",
    "                        pind = mulinp[pp]\n",
    "                        path[pind] += 1\n",
    "                        pre += [p[pp][path[pind]][1]]\n",
    "                        paths += [paths[-1].copy()+[p[pp][path[pind]][1]]]\n",
    "                        pp = p[pp][path[pind]][0]\n",
    "                r += [pre]\n",
    "                pp = mul[pind][0]\n",
    "                paths.pop()\n",
    "                pre = paths[-1].copy()\n",
    "                while pind > 0 and path[pind] == mul[pind][1]:\n",
    "                    path[pind] = -1\n",
    "                    for i in range(len(path)):\n",
    "                        if path[-1-i] != -1:\n",
    "                            pind = len(path)-i-1\n",
    "                            break\n",
    "                    pp = mul[pind][0]\n",
    "                    paths.pop()\n",
    "                    pre = paths[-1].copy()\n",
    "            return r\n",
    "\n",
    "    def ispalin(self, s):\n",
    "        i = 0\n",
    "        l = len(s)/2-1\n",
    "        while i <= l:\n",
    "            if s[i] != s[-i-1]:\n",
    "                return False\n",
    "            i += 1\n",
    "        return True"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "from typing import List\n",
    "import collections\n",
    "\n",
    "class Solution:\n",
    "    def partition(self, s: str) -> List[List[str]]:\n",
    "        def is_re(word):\n",
    "            word_len = len(word)\n",
    "            if word ==1:\n",
    "                return True\n",
    "            left = 0\n",
    "            right = word_len-1\n",
    "            while left<=right:\n",
    "                if word[left] != word[right]:\n",
    "                    return False\n",
    "                left+=1\n",
    "                right-=1\n",
    "            return True\n",
    "         \n",
    "        s_len = len(s)\n",
    "\n",
    "        s_list = [[s[i]] for i in range(s_len)]\n",
    "        for i in range(s_len-1,-1,-1):\n",
    "            for j in range(i-1,  -1,-1):\n",
    "                w = s[j:i+1]\n",
    "                if is_re(w):\n",
    "                    s_list[i].append(w)\n",
    "        # print(s_list)\n",
    "        def dfs(i):\n",
    "            if i<0:\n",
    "                return \n",
    "            cur = []\n",
    "            for w in s_list[i]:\n",
    "                word = dfs(i-len(w))\n",
    "                if word:\n",
    "                    for v in word:\n",
    "                        v.append(w)\n",
    "                        cur.append(v)\n",
    "                else:\n",
    "                    cur.append([w])\n",
    "            return cur\n",
    "        return dfs(s_len-1)\n",
    "\n",
    "            "
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "from typing import List\n",
    "import collections\n",
    "\n",
    "class Solution:\n",
    "    def partition(self, s: str) -> List[List[str]]:\n",
    "        def is_re(word):\n",
    "            word_len = len(word)\n",
    "            if word ==1:\n",
    "                return True\n",
    "            left = 0\n",
    "            right = word_len-1\n",
    "            while left<=right:\n",
    "                if word[left] != word[right]:\n",
    "                    return False\n",
    "                left+=1\n",
    "                right-=1\n",
    "            return True\n",
    "         \n",
    "        s_len = len(s)\n",
    "\n",
    "        s_list = [[s[i]] for i in range(s_len)]\n",
    "        for i in range(s_len):\n",
    "            for j in range(i+2, s_len+1):\n",
    "                w = s[i:j]\n",
    "                if is_re(w):\n",
    "                    s_list[i].append(w)\n",
    "        # print(s_list)\n",
    "        def dfs(i):\n",
    "            if i>=s_len:\n",
    "                return []\n",
    "            cur = []\n",
    "            for w in s_list[i]:\n",
    "                word = dfs(i+len(w))\n",
    "                if word:\n",
    "                    for v in word:\n",
    "                        cur.append([w]+v)\n",
    "                else:\n",
    "                    cur.append([w])\n",
    "            return cur\n",
    "        return dfs(0)\n",
    "            "
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "from typing import List\n",
    "import collections\n",
    "\n",
    "class Solution:\n",
    "    def partition(self, s: str) -> List[List[str]]:\n",
    "        res = []\n",
    "        self.backtracking(s, 0, [], res)\n",
    "        return res\n",
    "\n",
    "    def backtracking(self, s, start, data, res):\n",
    "        if start > len(s):\n",
    "            return\n",
    "\n",
    "        if start == len(s):\n",
    "            res.append(data[:])\n",
    "            return\n",
    "\n",
    "        for i in range(start, len(s)):\n",
    "            cur = s[start: i + 1]\n",
    "            if self.is_para(cur):\n",
    "                data.append(cur)\n",
    "                self.backtracking(s, i + 1, data, res)\n",
    "                data.pop()\n",
    "\n",
    "\n",
    "    def is_para(self, input):\n",
    "        left, right = 0, len(input) - 1\n",
    "\n",
    "        while left < right and right > 0 and left < len(input):\n",
    "            if input[left] != input[right]:\n",
    "                return False\n",
    "            left += 1\n",
    "            right -= 1\n",
    "        return True"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "from typing import List\n",
    "import collections\n",
    "\n",
    "class Solution:\n",
    "    def partition(self, s: str) -> List[List[str]]:\n",
    "        res = []\n",
    "        def par(s):\n",
    "            return s==s[::-1]\n",
    "\n",
    "        def backtrack(path, res,s):\n",
    "            if not s:\n",
    "                res.append(copy.deepcopy(path))\n",
    "            for i in range(len(s)):\n",
    "                if par(s[:i+1]):\n",
    "                    path.append(s[:i+1])\n",
    "                    backtrack(path, res, s[i+1:])\n",
    "                    path.pop()\n",
    "            return res\n",
    "\n",
    "\n",
    "        res = backtrack([], [], s)\n",
    "        return res  ## 这种所有的方案就要用backtrack方法来解决\n"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "from typing import List\n",
    "import collections\n",
    "\n",
    "class Solution:\n",
    "    def partition(self, s: str) -> List[List[str]]:\n",
    "        # res = []\n",
    "        # path = []\n",
    "        # def backtrack(s, startIndex):\n",
    "        #     if startIndex >= len(s):\n",
    "        #         return res.append(path[:])\n",
    "        #     for i in range(startIndex, len(s)):\n",
    "        #         p = s[startIndex:i+1]\n",
    "        #         if p == p[::-1]:\n",
    "        #             path.append(p)\n",
    "        #         else:\n",
    "        #             continue\n",
    "        #         backtrack(s, i+1)\n",
    "        #         path.pop()\n",
    "        # backtrack(s, 0)\n",
    "        # return res\n",
    "\n",
    "\n",
    "        l=len(s)\n",
    "        dp=[[] for _ in range(l+1)]\n",
    "        dp[0]=[[]]\n",
    "        for i in range(1,l+1):\n",
    "            for j in range(i):\n",
    "                tmp=s[j:i]\n",
    "                if tmp==tmp[::-1]:\n",
    "                    dp[i] += [x+[tmp] for x in dp[j]]\n",
    "        return dp[-1]"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "from typing import List\n",
    "import collections\n",
    "\n",
    "class Solution:\n",
    "    def partition(self, s: str) -> List[List[str]]:\n",
    "        # res = []\n",
    "        # path = []\n",
    "        # def backtrack(s, startIndex):\n",
    "        #     if startIndex >= len(s):\n",
    "        #         return res.append(path[:])\n",
    "        #     for i in range(startIndex, len(s)):\n",
    "        #         p = s[startIndex:i+1]\n",
    "        #         if p == p[::-1]:\n",
    "        #             path.append(p)\n",
    "        #         else:\n",
    "        #             continue\n",
    "        #         backtrack(s, i+1)\n",
    "        #         path.pop()\n",
    "        # backtrack(s, 0)\n",
    "        # return res\n",
    "\n",
    "\n",
    "        l=len(s)\n",
    "        dp=[[] for _ in range(l+1)]\n",
    "        dp[0]=[[]]\n",
    "        for i in range(1,l+1):\n",
    "            for j in range(i):\n",
    "                tmp=s[j:i]\n",
    "                if tmp==tmp[::-1]:\n",
    "                    dp[i] += [x+[tmp] for x in dp[j]]\n",
    "        return dp[-1]"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "from typing import List\n",
    "import collections\n",
    "\n",
    "class Solution:\n",
    "    def partition(self, s: str) -> List[List[str]]:\n",
    "        n = len(s)\n",
    "        ans = []\n",
    "        substr_list = []\n",
    "\n",
    "        def dfs(i):\n",
    "            if i >= n:\n",
    "                if substr_list:\n",
    "                    ans.append(list(substr_list))\n",
    "                return\n",
    "            for j in range(i, n):\n",
    "                if s[i:j + 1] == s[i:j + 1][::-1]:\n",
    "                    substr_list.append(s[i:j + 1])\n",
    "                    dfs(j + 1)\n",
    "                    substr_list.pop()\n",
    "\n",
    "        dfs(0)\n",
    "        return ans"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "from typing import List\n",
    "import collections\n",
    "\n",
    "class Solution:\n",
    "    def partition(self, s: str) -> List[List[str]]:\n",
    "        ans = []\n",
    "        state = []\n",
    "        n = len(s)\n",
    "        def dfs(i):\n",
    "            if i == n:\n",
    "                ans.append(state[:])\n",
    "            \n",
    "            for j in range(i, n):\n",
    "                if s[i:j+1] == s[i:j+1][::-1]:\n",
    "                    state.append(s[i:j+1])\n",
    "                    dfs(j+1)\n",
    "                    state.pop()\n",
    "        \n",
    "        dfs(0)\n",
    "\n",
    "        return ans\n"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "from typing import List\n",
    "import collections\n",
    "\n",
    "class Solution:\n",
    "    def partition(self, s: str) -> List[List[str]]:\n",
    "        dp = [[False] * len(s) for _ in range(len(s))]\n",
    "        for i in range(len(s) - 1, -1, -1):\n",
    "            for j in range(i, len(s)):\n",
    "                if s[i] == s[j]:\n",
    "                    if j - i <= 1:\n",
    "                        dp[i][j] = True\n",
    "                    elif dp[i + 1][j - 1]:\n",
    "                        dp[i][j] = True\n",
    "        result = []\n",
    "        path = []\n",
    "        def backtracking(start):\n",
    "            if start == len(s):\n",
    "                result.append(path[:])\n",
    "                return\n",
    "            for i in range(start, len(s)):\n",
    "                if dp[start][i]:\n",
    "                    path.append(s[start:i + 1])\n",
    "                    backtracking(i + 1)\n",
    "                    path.pop()\n",
    "        backtracking(0)\n",
    "        return result\n"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "from typing import List\n",
    "import collections\n",
    "\n",
    "class Solution:\n",
    "    def partition(self, s: str) -> List[List[str]]:\n",
    "        n = len(s)\n",
    "        ans = []\n",
    "        path = []\n",
    "\n",
    "        def dfs(i, start):\n",
    "            if i == n:\n",
    "                ans.append(path[:])\n",
    "                return\n",
    "\n",
    "            if i < n - 1:\n",
    "                dfs(i + 1, start)\n",
    "            \n",
    "            t = s[start: i + 1]\n",
    "            if t == t[::-1]:\n",
    "                path.append(t)\n",
    "                dfs(i+1, i+1)\n",
    "                path.pop()\n",
    "        \n",
    "        dfs(0, 0)\n",
    "        return ans"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "from typing import List\n",
    "import collections\n",
    "\n",
    "class Solution:\n",
    "    def partitionDisjoint(self, nums: List[int]) -> int:\n",
    "        n = len(nums)\n",
    "        cur_max = left_max = nums[0]\n",
    "        left_pos = 0\n",
    "        for i in range(1, n - 1):\n",
    "            if nums[i] > cur_max:\n",
    "                cur_max = nums[i]\n",
    "            if nums[i] < left_max:\n",
    "                left_max, left_pos = cur_max, i\n",
    "        return left_pos + 1\n"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "from typing import List\n",
    "import collections\n",
    "\n",
    "class Solution:\n",
    "    def partitionDisjoint(self, nums: List[int]) -> int:\n",
    "        left = 1\n",
    "        leftMax = nums[0]\n",
    "        curMax = nums[0]\n",
    "        for i, x in enumerate(nums):\n",
    "            if x < leftMax:\n",
    "                left = i+1\n",
    "                leftMax = curMax\n",
    "            curMax = max(curMax, x)\n",
    "        return left"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "from typing import List\n",
    "import collections\n",
    "\n",
    "class Solution:\n",
    "    def partitionDisjoint(self, nums: List[int]) -> int:\n",
    "        post_min = [0] * len(nums)\n",
    "        post_min[-1] = nums[-1]\n",
    "        for i in range(len(nums) - 2, -1, -1):\n",
    "            post_min[i] = min(post_min[i + 1], nums[i])\n",
    "\n",
    "        pre_max = 0\n",
    "        for i in range(0, len(nums) - 1):\n",
    "            pre_max = max(pre_max, nums[i])\n",
    "            if pre_max <= post_min[i + 1]:\n",
    "                return i + 1\n",
    "\n"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "from typing import List\n",
    "import collections\n",
    "\n",
    "class Solution:\n",
    "    def partitionDisjoint(self, nums: List[int]) -> int:\n",
    "        left = 1\n",
    "        leftMax = nums[0]\n",
    "        curMax = nums[0]\n",
    "        for i, x in enumerate(nums):\n",
    "            if x < leftMax:\n",
    "                left = i+1\n",
    "                leftMax = curMax\n",
    "            curMax = max(curMax, x)\n",
    "        return left"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "from typing import List\n",
    "import collections\n",
    "\n",
    "class Solution:\n",
    "    def partitionDisjoint(self, nums: List[int]) -> int:\n",
    "        n = len(nums)\n",
    "        leftmax = nums[0]\n",
    "        leftnums = [nums[0]]\n",
    "        start = 1\n",
    "        while True:\n",
    "            a = min(nums[start:])\n",
    "            if leftmax > a:  # 如果左边的最大值大于右边的最小值\n",
    "                start = nums[start:].index(a)+start+1\n",
    "                leftnums = nums[:start]\n",
    "                leftmax = max(leftnums)\n",
    "            else:\n",
    "                return len(leftnums)\n",
    "\n"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "from typing import List\n",
    "import collections\n",
    "\n",
    "class Solution:\n",
    "    def partitionDisjoint(self, nums: List[int]) -> int:\n",
    "        n = len(nums)\n",
    "        max_i = [-1] * (n+2)\n",
    "        min_i = [10000001] * (n+2)\n",
    "        for i in range(n):\n",
    "            max_i[i] = max(max_i[i-1], nums[i])\n",
    "        for i in range(n-1, -1, -1):\n",
    "            min_i[i] = min(min_i[i+1], nums[i])\n",
    "        res = 0\n",
    "        for i in range(n-1):\n",
    "            if max_i[i] <= min_i[i+1]:\n",
    "                res = i+1\n",
    "                break\n",
    "        # print(max_i, min_i)\n",
    "        return res"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "from typing import List\n",
    "import collections\n",
    "\n",
    "class Solution:\n",
    "    def partitionDisjoint(self, nums: List[int]) -> int:\n",
    "        n = len(nums)\n",
    "        right_min = [0 for _ in range(n)]\n",
    "        right_min[-1] = nums[-1]\n",
    "\n",
    "        for i in range(n - 2, 0, -1):\n",
    "            right_min[i] = min(right_min[i + 1], nums[i])\n",
    "\n",
    "        \n",
    "        # print(right_min)\n",
    "        left_max = nums[0]\n",
    "        for i in range(1, n):\n",
    "            if left_max <= right_min[i]:\n",
    "                return i\n",
    "\n",
    "            if nums[i] > left_max:\n",
    "               left_max = nums[i]\n",
    "            # print(i, left_max, right_min[i])\n",
    "        "
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "from typing import List\n",
    "import collections\n",
    "\n",
    "class Solution:\n",
    "    def partitionDisjoint(self, nums: List[int]) -> int:\n",
    "        n = len(nums)\n",
    "        r_min = [0] * (n - 1) + [nums[-1]]\n",
    "        for i in range(n - 2, -1, -1):\n",
    "            r_min[i] = min(r_min[i + 1], nums[i])\n",
    "        pre_max = nums[0]\n",
    "        for i in range(1, n):\n",
    "            if pre_max <= r_min[i]:\n",
    "                return i\n",
    "            pre_max = max(pre_max, nums[i])\n",
    "\n",
    "\n",
    "\n",
    "        "
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "from typing import List\n",
    "import collections\n",
    "\n",
    "class Solution:\n",
    "    def partitionDisjoint(self, nums: List[int]) -> int:\n",
    "        n = len(nums)\n",
    "        maxs, mins = [-1] * n, [inf] * n\n",
    "        for i, num in enumerate(nums):\n",
    "            maxs[i] = max(maxs[i - 1], num)\n",
    "        for i in range(n - 1, -1, -1):\n",
    "            mins[i] = min(mins[i + 1] if i < n -1 else inf, nums[i])\n",
    "        for i in range(1, n):\n",
    "            if maxs[i - 1] <= mins[i]:\n",
    "                return i\n",
    "        return -1"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "from typing import List\n",
    "import collections\n",
    "\n",
    "class Solution:\n",
    "    def partitionDisjoint(self, nums: List[int]) -> int:\n",
    "        n = len(nums)\n",
    "        right_min = [0 for _ in range(n)]\n",
    "        right_min[-1] = nums[-1]\n",
    "\n",
    "        for i in range(n - 2, -1, -1):\n",
    "            if nums[i] < right_min[i + 1]:\n",
    "                right_min[i] = nums[i]\n",
    "            else:\n",
    "                right_min[i] = right_min[i + 1]\n",
    "        \n",
    "        left_max = nums[0]\n",
    "        for i in range(1, n):\n",
    "            if left_max <= right_min[i]:\n",
    "                return i\n",
    "\n",
    "            if nums[i] > left_max:\n",
    "               left_max = nums[i]\n",
    "        "
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "from typing import List\n",
    "import collections\n",
    "\n",
    "class Solution:\r\n",
    "    def partitionDisjoint(self, nums: List[int]) -> int:\r\n",
    "        right=[inf]*(len(nums)+1)\r\n",
    "        for i in range(len(nums)-1,-1,-1):\r\n",
    "            right[i]=min(right[i+1],nums[i])\r\n",
    "        ma=0\r\n",
    "        print(right)\r\n",
    "        for i in range(len(nums)):\r\n",
    "            ma=max(ma,nums[i])\r\n",
    "            if ma<=right[i+1]:\r\n",
    "                return i+1"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "from typing import List\n",
    "import collections\n",
    "\n",
    "import sys\n",
    "from typing import List\n",
    "\n",
    "\n",
    "class Solution:\n",
    "    def partitionDisjoint(self, nums: List[int]) -> int:\n",
    "        left_b = [0 for _ in range(len(nums))]\n",
    "        left_b[0] = nums[0]\n",
    "        for i in range(1, len(nums)):\n",
    "            left_b[i] = max(left_b[i - 1], nums[i])\n",
    "            pass\n",
    "        right_s = [0 for _ in range(len(nums))]\n",
    "        right_s[len(nums) - 1 - 1] = nums[len(nums) - 1]\n",
    "        p = len(nums) - 1 - 1 - 1\n",
    "        while p >= 0:\n",
    "            right_s[p] = min(right_s[p + 1], nums[p + 1])\n",
    "            p -= 1\n",
    "            pass\n",
    "\n",
    "        for i in range(len(nums)):\n",
    "            if left_b[i] <= right_s[i] :\n",
    "                return i + 1\n",
    "            pass\n",
    "\n",
    "    pass\n"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "from typing import List\n",
    "import collections\n",
    "\n",
    "class Solution:\r\n",
    "    def partitionDisjoint(self, nums: list[int]) -> int:\r\n",
    "        max_arr = []\r\n",
    "        min_arr = []\r\n",
    "        for i in range(len(nums) - 1):\r\n",
    "            if i == 0:\r\n",
    "                max_arr.append(nums[i])\r\n",
    "            else:\r\n",
    "                max_arr.append(max(max_arr[-1], nums[i]))\r\n",
    "        for i in range(len(nums) - 1, 0, -1):\r\n",
    "            if i == len(nums) - 1:\r\n",
    "                min_arr.append(nums[i])\r\n",
    "            else:\r\n",
    "                min_arr.append(min(min_arr[-1], nums[i]))\r\n",
    "        min_arr.reverse()\r\n",
    "        for i in range(len(nums)):\r\n",
    "            if max_arr[i] <= min_arr[i]:\r\n",
    "                return i + 1"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "from typing import List\n",
    "import collections\n",
    "\n",
    "class Solution:\n",
    "    def partitionDisjoint(self, nums: List[int]) -> int:\n",
    "        left_max, right_min = [nums[0]], [nums[-1]]\n",
    "        for i in range(1, len(nums)):\n",
    "            left_max.append(max(left_max[-1], nums[i]))\n",
    "            right_min.append(min(right_min[-1], nums[len(nums) - i - 1]))\n",
    "        for i in range(len(nums)):\n",
    "            if left_max[i] <= right_min[len(nums) - i - 2]:\n",
    "                return i + 1"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "from typing import List\n",
    "import collections\n",
    "\n",
    "class Solution:\n",
    "    def partitionDisjoint(self, nums: List[int]) -> int:\n",
    "        M = len(nums)\n",
    "        left = [nums[0]] + [0] * (M - 1)\n",
    "        for i in range(1, M):\n",
    "            left[i] = max(left[i - 1], nums[i])\n",
    "        right = [0] * (M - 1) + [nums[-1]]\n",
    "        for i in range(M - 2, -1, -1):\n",
    "            right[i] = min(right[i + 1], nums[i])\n",
    "        for i in range(M):\n",
    "            if left[i] <= right[i + 1]:\n",
    "                return i + 1\n",
    "        return -1"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "from typing import List\n",
    "import collections\n",
    "\n",
    "class Solution:\n",
    "    def partitionDisjoint(self, nums: List[int]) -> int:\n",
    "        n = len(nums)\n",
    "        left = [nums[0]] + [0] * (n - 1)\n",
    "        right = [inf] * (n - 1) + [nums[-1]]\n",
    "        for i in range(1, n):\n",
    "            left[i] = max(left[i - 1], nums[i])\n",
    "        for j in range(n - 2, -1, -1):\n",
    "            right[j] = min(right[j + 1], nums[j])\n",
    "        for k in range(n - 1):\n",
    "            if left[k] <= right[k + 1]:\n",
    "                return k + 1"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "from typing import List\n",
    "import collections\n",
    "\n",
    "class Solution:\n",
    "    def partitionDisjoint(self, nums: List[int]) -> int:\n",
    "        idx = sorted(range(len(nums)), key=lambda x : nums[x])\n",
    "        max_v = 0\n",
    "        for i in range(len(idx)):\n",
    "            max_v = max(max_v, idx[i])\n",
    "            if i == max_v:\n",
    "                return i + 1"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "from typing import List\n",
    "import collections\n",
    "\n",
    "class Solution:\n",
    "    def partitionDisjoint(self, nums: List[int]) -> int:\n",
    "        n = len(nums)\n",
    "\n",
    "        prefixMax = []\n",
    "        m = 0\n",
    "        for v in nums:\n",
    "            m = max(v, m)\n",
    "            prefixMax.append(m)\n",
    "\n",
    "        \n",
    "        suffixMin = []\n",
    "        m = 10_000_000\n",
    "        for v in reversed(nums):\n",
    "            m = min(m, v)\n",
    "            suffixMin.append(m)\n",
    "\n",
    "        suffixMin = list(reversed(suffixMin))\n",
    "        print(prefixMax)\n",
    "        print(suffixMin)\n",
    "\n",
    "        for i, (M, m) in enumerate(zip(prefixMax[:-1], suffixMin[1:])):\n",
    "            if M <= m:\n",
    "                return i + 1\n",
    "\n",
    "\n",
    "\n",
    "\n"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "from typing import List\n",
    "import collections\n",
    "\n",
    "class Solution:\n",
    "    def partitionDisjoint(self, nums: List[int]) -> int:\n",
    "        # 存储包括此数值以后的最小值\n",
    "        min_values = [ None for _ in range(len(nums))]\n",
    "        max_values = [ None for _ in range(len(nums))]\n",
    "        min_value = nums[-1]\n",
    "        max_value = nums[0]\n",
    "        for i in range(-2,-len(nums)-1,-1):\n",
    "            min_value = min(nums[i+1], min_value)\n",
    "            min_values[i] = min_value\n",
    "\n",
    "        for i in range(0,len(nums),1):\n",
    "            max_value = max(nums[i], max_value)\n",
    "            max_values[i] = max_value\n",
    "\n",
    "        print(max_values, min_values)\n",
    "\n",
    "        for i, maxv, minv in zip(range(len(nums)), max_values, min_values):\n",
    "            print(i, maxv, minv)\n",
    "            if maxv <= minv:\n",
    "                return i+1"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "from typing import List\n",
    "import collections\n",
    "\n",
    "class Solution:\n",
    "    def partitionDisjoint(self, nums: List[int]) -> int:\n",
    "        a = Counter(nums)\n",
    "        seen = set()\n",
    "        r = []\n",
    "        for i in a:\n",
    "            r.append(i)\n",
    "        r.sort()    \n",
    "        max_val = nums[0]\n",
    "        min_val = r[0]\n",
    "        i = 0\n",
    "        j = 0\n",
    "        ans = 0\n",
    "        while max_val > min_val:\n",
    "            max_val = max(max_val,nums[j])\n",
    "            a[nums[j]] -= 1\n",
    "            j += 1\n",
    "            while a[min_val] == 0:\n",
    "                i += 1\n",
    "                min_val = r[i]\n",
    "            ans += 1\n",
    "        return 1 if ans == 0 else ans   \n"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "from typing import List\n",
    "import collections\n",
    "\n",
    "class Solution:\n",
    "    def partitionDisjoint(self, nums: List[int]) -> int:\n",
    "        count = defaultdict(int)\n",
    "        for i in nums:\n",
    "            count[i]+=1\n",
    "        nums_sort = sorted(nums,reverse=True)\n",
    "        max_l = 0\n",
    "        min_r = nums_sort.pop()\n",
    "        for i in range(len(nums)-1):\n",
    "            count[nums[i]]-=1\n",
    "            max_l = max([max_l,nums[i]])\n",
    "            if min_r == nums[i]:\n",
    "                while count[min_r] == 0:\n",
    "                    min_r = nums_sort.pop()\n",
    "            if max_l <= min_r:\n",
    "                return i+1"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "from typing import List\n",
    "import collections\n",
    "\n",
    "class Solution:\n",
    "    def partitionDisjoint(self, nums: List[int]) -> int:\n",
    "        n = len(nums)\n",
    "        l_max = [nums[0]]\n",
    "        r_min = [nums[-1]]\n",
    "\n",
    "        for i in range(1, n):\n",
    "            l_max.append(max(l_max[-1], nums[i]))\n",
    "            r_min.append(min(r_min[-1], nums[n-1-i]))\n",
    "        print(l_max)\n",
    "        print(r_min)\n",
    "\n",
    "        for k in range(n):\n",
    "            if l_max[k] <= r_min[n-2-k]:\n",
    "                return k + 1\n"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "from typing import List\n",
    "import collections\n",
    "\n",
    "class Solution:\n",
    "    def partitionDisjoint(self, nums: List[int]) -> int:\n",
    "        n = len(nums)\n",
    "        l_max = [nums[0]]\n",
    "        r_min = [nums[-1]]\n",
    "\n",
    "        for i in range(1, n):\n",
    "            l_max.append(max(l_max[-1], nums[i]))\n",
    "            r_min.append(min(r_min[-1], nums[n-1-i]))\n",
    "        print(l_max)\n",
    "        print(r_min)\n",
    "\n",
    "        for k in range(n):\n",
    "            if l_max[k] <= r_min[n-2-k]:\n",
    "                return k + 1\n"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "from typing import List\n",
    "import collections\n",
    "\n",
    "import itertools\n",
    "class Solution:\n",
    "    def partitionDisjoint(self, nums: List[int]) -> int:\n",
    "        ma = list(itertools.accumulate(nums, max))\n",
    "        mi = list(itertools.accumulate(nums[::-1], min))[::-1]\n",
    "        for idx, (a, i) in enumerate(zip([float('+inf')] + ma, mi + [float('-inf')])):\n",
    "            if a <= i:\n",
    "                return idx\n"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "from typing import List\n",
    "import collections\n",
    "\n",
    "class Solution:\n",
    "    def partitionDisjoint(self, nums: List[int]) -> int:\n",
    "        max_l=nums[0]\n",
    "        c = Counter(nums[1:])\n",
    "        l = sorted(c.keys(), reverse=True)\n",
    "        for i in range(1, len(nums)):\n",
    "            if l[-1]>=max_l: return i\n",
    "            c[nums[i]] -= 1\n",
    "            max_l = max(max_l, nums[i])\n",
    "            while c[l[-1]]==0: l.pop()\n",
    "        return len(i)-1\n",
    "\n",
    "        "
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "from typing import List\n",
    "import collections\n",
    "\n",
    "class Solution:\n",
    "    def partitionDisjoint(self, nums: List[int]) -> int:\n",
    "        l = len(nums)\n",
    "        min_arr = [nums[-1] for i in range(l)]\n",
    "        min_num = nums[-1]\n",
    "        max_num = nums[0]\n",
    "        max_arr = [nums[0] for i in range(l)]\n",
    "        for i, n in enumerate(nums[::-1]):\n",
    "            min_num = min(min_num, n)\n",
    "            min_arr[l-1-i] = min_num\n",
    "        \n",
    "        for i, n in enumerate(nums):\n",
    "            max_num = max(max_num, n)\n",
    "            max_arr[i] = max_num\n",
    "        \n",
    "        print(min_arr)\n",
    "        print(max_arr)\n",
    "\n",
    "        for i in range(l-1):\n",
    "            if max_arr[i] <= min_arr[i+1]:\n",
    "                return i+1\n",
    "        return 1\n",
    "            "
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "from typing import List\n",
    "import collections\n",
    "\n",
    "class Solution:\n",
    "    def partitionDisjoint(self, nums: List[int]) -> int:\n",
    "        minn = [1000000000]*len(nums)\n",
    "        minn[-1] = nums[-1]\n",
    "        maxx = [-1]*len(nums)\n",
    "        maxx[0] = nums[0]\n",
    "        for i in range(1,len(nums)):\n",
    "            maxx[i] = max(maxx[i-1],nums[i])\n",
    "            minn[len(nums)-1-i] = min(minn[len(nums)-1-i+1],nums[len(nums)-1-i])\n",
    "        print(maxx)\n",
    "        print(minn)\n",
    "        for i in range(1,len(nums)):\n",
    "            if maxx[i-1]<=minn[i]:\n",
    "                return i"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "from typing import List\n",
    "import collections\n",
    "\n",
    "class Solution:\n",
    "    def partitionDisjoint(self, nums: List[int]) -> int:\n",
    "        pre_max = [0] * len(nums)\n",
    "        pre_max[0] = nums[0]\n",
    "        for i in range(1, len(nums)):\n",
    "            pre_max[i] = max(pre_max[i - 1], nums[i])\n",
    "\n",
    "        post_min = [0] * len(nums)\n",
    "        post_min[-1] = nums[-1]\n",
    "        for i in range(len(nums) - 2, -1, -1):\n",
    "            post_min[i] = min(post_min[i + 1], nums[i])\n",
    "\n",
    "        print(pre_max, post_min)\n",
    "\n",
    "        for i in range(len(nums) - 1):\n",
    "            if pre_max[i] <= post_min[i + 1]:\n",
    "                return i+1\n"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "from typing import List\n",
    "import collections\n",
    "\n",
    "class Solution:\n",
    "    def partitionDisjoint(self, nums: List[int]) -> int:\n",
    "\n",
    "        nums_sort=sorted(nums)\n",
    "        ref={}\n",
    "        for i,x in enumerate(nums_sort,1):\n",
    "            if x not in ref:\n",
    "                ref[x]=i\n",
    "\n",
    "        c=0\n",
    "        cnt=0\n",
    "        for i,x in enumerate(nums,1):\n",
    "            if ref[x]>c:\n",
    "                c=ref[x]\n",
    "                cnt=0\n",
    "            elif ref[x]==c:\n",
    "                cnt+=1\n",
    "            if c+cnt==i:\n",
    "                return i"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "from typing import List\n",
    "import collections\n",
    "\n",
    "class Solution:\n",
    "    def partitionDisjoint(self, nums: List[int]) -> int:\n",
    "        leftMax, rightMin = float(\"-inf\"), float(\"inf\")\n",
    "        n = len(nums)\n",
    "        tmp = [[None] * 2 for _ in range(n - 1)]\n",
    "\n",
    "        for l in range(1, n):\n",
    "            leftMax = max(leftMax, nums[l - 1])\n",
    "            rightMin = min(rightMin, nums[n - l])\n",
    "            tmp[l - 1][0] = leftMax\n",
    "            tmp[n - 1 - l][1] = rightMin\n",
    "\n",
    "        for i in range(n - 1):\n",
    "            if tmp[i][0] <= tmp[i][1]:\n",
    "                return i + 1"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "from typing import List\n",
    "import collections\n",
    "\n",
    "class Solution:\n",
    "    def partitionDisjoint(self, nums: List[int]) -> int:\n",
    "        # 懒删除堆  哈希表 + 队就性\n",
    "        mx = 0\n",
    "        n = len(nums)\n",
    "        m = Counter(nums)\n",
    "        h = nums.copy()\n",
    "        heapify(h)\n",
    "\n",
    "        for i in range(n-1):\n",
    "            mx = max(mx, nums[i])\n",
    "            m[nums[i]] -= 1\n",
    "            while m[h[0]] == 0:\n",
    "                heappop(h)\n",
    "            if h[0] >= mx:\n",
    "                return i+1"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "from typing import List\n",
    "import collections\n",
    "\n",
    "class Solution:\n",
    "    def partitionDisjoint(self, nums: List[int]) -> int:\n",
    "       q,e=[nums[-1]],[nums[0]]\n",
    "       pr=nums[0]\n",
    "       for x in nums[1:]:\n",
    "           if x>pr:\n",
    "             e.append(x)\n",
    "           else:\n",
    "             e.append(pr)\n",
    "           pr=max(pr,x)\n",
    "       pr=nums[-1]    \n",
    "       for x in nums[1:-1][::-1]:\n",
    "           if x>pr:\n",
    "             q.append(pr)\n",
    "           else:\n",
    "             q.append(x)\n",
    "           pr=min(pr,x)\n",
    "       q=q[::-1] \n",
    "       print(q,e)\n",
    "       i=0\n",
    "       for x,y in zip(q,e):\n",
    "         if x>=y:\n",
    "           return i+1\n",
    "         i+=1    \n",
    "\n",
    "       "
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "from typing import List\n",
    "import collections\n",
    "\n",
    "class Solution:\n",
    "    def partitionDisjoint(self, nums: List[int]) -> int:\n",
    "        n = len(nums)\n",
    "        record = [[nums[0], nums[-1]] for each in range(n)]\n",
    "        for i in range(1, n):\n",
    "            record[i][0] = max(record[i-1][0], nums[i])\n",
    "            record[n - i - 1][1] = min(record[n - i][1], nums[n - i - 1])\n",
    "        for i in range(len(record)):\n",
    "            if record[i][0] <= record[i + 1][1]:\n",
    "                return i + 1\n",
    "\n",
    "\n",
    "        "
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "from typing import List\n",
    "import collections\n",
    "\n",
    "class Solution:\n",
    "    def partitionDisjoint(self, nums: List[int]) -> int:\n",
    "        ans = 1\n",
    "        ma_left = nums[0]\n",
    "        d = collections.Counter(nums[ans:])\n",
    "        lis = list(set(nums[1:]))\n",
    "        lis.sort()\n",
    "        lis = lis[::-1]\n",
    "        mi_right = lis[-1]\n",
    "        for i in range(len(nums)-1):\n",
    "            if ma_left <= mi_right:\n",
    "                return ans\n",
    "            d[nums[ans]] -= 1\n",
    "            \n",
    "            while not d[mi_right]:\n",
    "                lis.pop()\n",
    "                mi_right = lis[-1]\n",
    "\n",
    "            ma_left = max(ma_left,nums[ans])\n",
    "            ans += 1\n"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "from typing import List\n",
    "import collections\n",
    "\n",
    "class Solution:\n",
    "    def partitionDisjoint(self, nums: List[int]) -> int:\n",
    "        dic = {}\n",
    "        ll = len(nums)\n",
    "        tleft = nums[0]\n",
    "        for i, x in enumerate(nums):\n",
    "            dic[x] = i\n",
    "        dic = sorted(dic.items(), reverse=True)\n",
    "        t = dic[-1][1]\n",
    "        # print(dic)\n",
    "        i = 0\n",
    "        while tleft > dic[-1][0]:\n",
    "            for i in range(i, t+1):\n",
    "                # print(i)\n",
    "                tleft = max(tleft, nums[i])\n",
    "            i += 1\n",
    "            while dic[-1][1] < i:\n",
    "                dic.pop()\n",
    "            t = dic[-1][1]\n",
    "            # print(i)\n",
    "            # print(dic)\n",
    "            # break\n",
    "        return max(1, i)\n",
    "            "
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "from typing import List\n",
    "import collections\n",
    "\n",
    "class Solution:\n",
    "    def partitionDisjoint(self, nums: List[int]) -> int:\n",
    "        t = sorted((j,i) for i,j in enumerate(nums))\n",
    "        a = 0\n",
    "        m = 0\n",
    "        for i ,j in t:\n",
    "            a = max(a,j)\n",
    "            if m == a:\n",
    "                return m + 1\n",
    "            m += 1 "
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "from typing import List\n",
    "import collections\n",
    "\n",
    "class Solution:\n",
    "    def partitionDisjoint(self, nums: List[int]) -> int:\n",
    "        a = {}\n",
    "        for num in nums:\n",
    "            if num in a:\n",
    "                a[num] += 1\n",
    "            else:\n",
    "                a[num] = 1\n",
    "        n = len(nums)\n",
    "        maxl = 0\n",
    "        minr = min(nums)\n",
    "        for i in range(n):\n",
    "            maxl = max(maxl,nums[i])\n",
    "            a[nums[i]] -= 1\n",
    "            if a[nums[i]] == 0:\n",
    "                a.pop(nums[i])\n",
    "            if nums[i] == minr:\n",
    "                minr = min(a.keys())\n",
    "            if maxl <= minr:\n",
    "                return i+1\n",
    "        \n",
    "\n",
    "\n"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "from typing import List\n",
    "import collections\n",
    "\n",
    "\n",
    "class Solution:\n",
    "    def partitionDisjoint(self, A: List[int]) -> int:\n",
    "        n = len(A)\n",
    "\n",
    "        self.tree = [None] * (n * 4 + 1)\n",
    "\n",
    "        def build_tree(tree_index, left, right):\n",
    "            if left == right:\n",
    "                self.tree[tree_index] = (A[left], A[left])\n",
    "                return self.tree[tree_index]\n",
    "            else:\n",
    "                mid = left + (right - left) // 2\n",
    "                left_c_id = tree_index * 2\n",
    "                right_c_id = left_c_id + 1\n",
    "                lm = build_tree(left_c_id, left, mid)\n",
    "                rm = build_tree(right_c_id, mid + 1, right)\n",
    "                self.tree[tree_index] = min(lm[0], rm[0]), max(lm[1], rm[1])\n",
    "                return self.tree[tree_index] \n",
    "        \n",
    "        def search(tree_index, l, r, ql, qr):\n",
    "            if l == ql and r == qr:\n",
    "                return self.tree[tree_index]\n",
    "            \n",
    "            mid = l + (r - l) // 2\n",
    "            left_c_id = tree_index * 2\n",
    "            right_c_id = left_c_id + 1\n",
    "\n",
    "            if qr <= mid:\n",
    "                return search(left_c_id, l, mid, ql, qr)\n",
    "            elif ql > mid:\n",
    "                return search(right_c_id, mid + 1, r, ql, qr)\n",
    "            else:\n",
    "                lm = search(left_c_id, l, mid, ql, mid)\n",
    "                rm = search(right_c_id, mid + 1, r, mid + 1, qr)\n",
    "                return min(lm[0], rm[0]), max(lm[1], rm[1])\n",
    "\n",
    "        build_tree(1, 0, n - 1)\n",
    "\n",
    "        for i in range(1, n):\n",
    "            left_max = search(1, 0, n - 1, 0, i - 1)[1]\n",
    "            right_min = search(1, 0, n - 1, i, n - 1)[0]\n",
    "            # print(left_max, right_min)\n",
    "            if left_max <= right_min:\n",
    "                return i"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "from typing import List\n",
    "import collections\n",
    "\n",
    "class Solution:\n",
    "    def partitionDisjoint(self, nums: List[int]) -> int:\n",
    "        # 剩余right的最小值要>= 左边的最大值\n",
    "        # 优先队列得到左边最大\n",
    "        # 小根堆得到右边最小\n",
    "        pq = []\n",
    "        heap = [(num,i) for i,num in enumerate(nums)]\n",
    "        heapify(heap)\n",
    "        for i,num in enumerate(nums):\n",
    "            while pq and num >= pq[-1]:\n",
    "                pq.pop()\n",
    "            pq.append(num)\n",
    "            while heap and heap[0][1] <= i:\n",
    "                heappop(heap)\n",
    "            if heap[0][0] >= pq[0]:\n",
    "                return i+1"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "from typing import List\n",
    "import collections\n",
    "\n",
    "class Solution:\n",
    "    def partitionDisjoint(self, nums: List[int]) -> int:\n",
    "        enum = list(enumerate(nums))\n",
    "        enum.sort(key=lambda a: a[1])\n",
    "        cnt = 0\n",
    "        max_idx = 0\n",
    "        for i in enum:\n",
    "            cnt += 1\n",
    "            max_idx = max(max_idx, i[0])\n",
    "            if cnt == max_idx+1:\n",
    "                return cnt\n",
    "        return -1"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "from typing import List\n",
    "import collections\n",
    "\n",
    "class Solution:\n",
    "    def partitionDisjoint(self, nums: List[int]) -> int:\n",
    "        # 剩余right的最小值要>= 左边的最大值\n",
    "        # 优先队列得到左边最大\n",
    "        # 小根堆得到右边最小\n",
    "        pq = []\n",
    "        heap = [(num,i) for i,num in enumerate(nums)]\n",
    "        heapify(heap)\n",
    "        for i,num in enumerate(nums):\n",
    "            while pq and num >= pq[-1]:\n",
    "                pq.pop()\n",
    "            pq.append(num)\n",
    "            while heap and heap[0][1] <= i:\n",
    "                heappop(heap)\n",
    "            if heap[0][0] >= pq[0]:\n",
    "                return i+1"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "from typing import List\n",
    "import collections\n",
    "\n",
    "class Solution:\n",
    "    def partitionDisjoint(self, nums: List[int]) -> int:\n",
    "        n = len(nums)\n",
    "        # mi = nums[-1]\n",
    "        # mii = n-1\n",
    "        # for i in range(len(nums)-1,0,-1):\n",
    "        #     if nums[0]>nums[i]:\n",
    "        #         break\n",
    "        #     if nums[i]<mi:\n",
    "        #         mi = nums[i]\n",
    "        #         mii = i\n",
    "        # else:\n",
    "        #     return 1\n",
    "        # ma = max(nums[:i+1])\n",
    "        # if ma<=mi: return i+1\n",
    "        # else:\n",
    "        #     ma = max(ma,max(nums[i+1:mii+1]))\n",
    "        lst = sorted((j,i) for i,j in enumerate(nums))\n",
    "        i = bisect_left(lst,nums[0],key=lambda x:x[0])\n",
    "        if i==0: return 1\n",
    "        m = max(lst[j][1] for j in range(i))\n",
    "        _m = m\n",
    "        for j in range(i+1,n):\n",
    "            if lst[j][1]<m:\n",
    "                m = _m\n",
    "            _m = max(_m,lst[j][1])\n",
    "        return m+1"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "from typing import List\n",
    "import collections\n",
    "\n",
    "class Solution:\n",
    "    def partitionDisjoint(self, nums: List[int]) -> int:\n",
    "        n, minv, maxv = len(nums), 1000010, -1\n",
    "        p = [[0 for i in range(2)] for j in range(n)]\n",
    "        for i in range(n):\n",
    "            maxv = max(maxv, nums[i])\n",
    "            minv = min(minv, nums[n - i - 1])\n",
    "            p[i][0] = maxv\n",
    "            p[n - i - 1][1] = minv\n",
    "        for i in range(n - 1):\n",
    "            if p[i][0] <= p[i + 1][1]:\n",
    "                return i + 1\n",
    "        return -1\n"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "from typing import List\n",
    "import collections\n",
    "\n",
    "class Solution:\n",
    "    def partitionDisjoint(self, nums: List[int]) -> int:\n",
    "        left_max = -1\n",
    "        remain = [(nums[i], i) for i in range(len(nums))]\n",
    "        heapq.heapify(remain)\n",
    "        for i in range(len(nums) - 1):\n",
    "            left_max = max(left_max, nums[i])\n",
    "            while remain[0][1] <= i:\n",
    "                heapq.heappop(remain)\n",
    "            if left_max <= remain[0][0]:\n",
    "                return i + 1\n",
    "        return -1\n"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "from typing import List\n",
    "import collections\n",
    "\n",
    "class Solution:\n",
    "    def partitionDisjoint(self, nums: List[int]) -> int:\n",
    "        heap, cur_max = [(v, i) for i, v in enumerate(nums)], nums[0]\n",
    "        heapq.heapify(heap)\n",
    "        for i, v in enumerate(nums):\n",
    "            if v > cur_max:\n",
    "                cur_max = v\n",
    "            while heap[0][1] <= i:\n",
    "                heapq.heappop(heap)\n",
    "            if cur_max <= heap[0][0]:\n",
    "                return i + 1"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "from typing import List\n",
    "import collections\n",
    "\n",
    "class Solution:\n",
    "    def partitionDisjoint(self, nums: List[int]) -> int:\n",
    "        # [5,0,3,8,6]\n",
    "        # [2,0,1,4,3]\n",
    "        # [1,1,1,0,6,12]\n",
    "        # [1,2,3,0,4,5]\n",
    "        n = len(nums)\n",
    "        sortNums = sorted(zip(nums, list(range(n))), key=lambda x: x[0])\n",
    "        sortIdx = [pair[1] for pair in sortNums]\n",
    "        minIdx = 0\n",
    "        for i, num in enumerate(sortIdx):\n",
    "            minIdx = max(minIdx, num)\n",
    "            if i == minIdx:\n",
    "                break\n",
    "        return i+1"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "from typing import List\n",
    "import collections\n",
    "\n",
    "class Solution:\n",
    "    def partitionDisjoint(self, nums: List[int]) -> int:\n",
    "        left = nums[0]\n",
    "        right = nums[-1]\n",
    "        max = [0]*len(nums)\n",
    "        min = [0]*len(nums)\n",
    "        for i,num in enumerate(nums):\n",
    "            if num > left:\n",
    "                left = num\n",
    "            max[i] = left\n",
    "        for i,num in reversed(list(enumerate(nums))):\n",
    "            if num < right:\n",
    "                right = num\n",
    "            min[i] = right\n",
    "        for i in range(0,len(nums)-1):\n",
    "            if max[i]<=min[i+1]:\n",
    "                return i+1\n"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "from typing import List\n",
    "import collections\n",
    "\n",
    "class Solution:\n",
    "    def partitionDisjoint(self, s: List[int]) -> int:\n",
    "        t = [(v, i) for i, v in enumerate(s)]\n",
    "        t.sort()\n",
    "        r = 0\n",
    "        for i, (a, b) in enumerate(t):\n",
    "            r = max(r, b)\n",
    "            if i == r:\n",
    "                return r + 1"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "from typing import List\n",
    "import collections\n",
    "\n",
    "def partdisjoin(nums):\n",
    "    heap = list(nums)\n",
    "    heapify(heap)\n",
    "    left_max=-1\n",
    "    i=0\n",
    "    while i < (len(nums)):\n",
    "        left_max = max(left_max, nums[i])\n",
    "        tmp=left_max\n",
    "        for j in range(i+1,len(nums)):\n",
    "            tmp=max(tmp, nums[j])\n",
    "            if nums[j] < left_max:\n",
    "                left_max=tmp\n",
    "                i = j-1\n",
    "                break\n",
    "        else:\n",
    "            return i+1\n",
    "        i+=1\n",
    "    # no return, inputs are garranted\n",
    "\n",
    "class ST:\n",
    "    def __init__(self, elems: List[int], op: Callable[[int, int], bool], e: Callable[[], int]) -> None:\n",
    "        self.op = op\n",
    "        self.e = e\n",
    "\n",
    "        def log2ceil(n):\n",
    "            r = 1\n",
    "            while r <= n:\n",
    "                r <<= 1\n",
    "            return r\n",
    "        self.sz = log2ceil(len(elems))\n",
    "        self.d = [e() for _ in range(2*self.sz)]\n",
    "        for i, x in enumerate(elems):\n",
    "            self.d[i+self.sz] = x\n",
    "        for i in range(self.sz-1, 0, -1):\n",
    "            self.update(i)\n",
    "\n",
    "    def update(self, i):\n",
    "        op = self.op\n",
    "\n",
    "        self.d[i] = op(self.d[i*2], self.d[i*2+1])\n",
    "\n",
    "    def prod(self, l, r):\n",
    "        op = self.op\n",
    "        lmv, rmv = self.e(), self.e()\n",
    "        l += self.sz\n",
    "        r += self.sz\n",
    "        while l < r:\n",
    "            if l & 1:\n",
    "                lmv = op(lmv, self.d[l])\n",
    "                l += 1\n",
    "            if r & 1:\n",
    "                r -= 1\n",
    "                rmv = op(self.d[r], rmv)\n",
    "            l //= 2\n",
    "            r //= 2\n",
    "        return op(lmv, rmv)\n",
    "\n",
    "\n",
    "def partdisjoin2(nums):\n",
    "    minval_st = ST(nums, min, lambda: float(\"inf\"))\n",
    "    maxval_st = ST(nums, max, lambda: -1)\n",
    "    for i in range(1,len(nums)):\n",
    "        if maxval_st.prod(0, i) <= minval_st.prod(i, len(nums)):\n",
    "            return i\n",
    "\n",
    "\n",
    "\n",
    "class Solution:\n",
    "    def partitionDisjoint(self, nums: List[int]) -> int:\n",
    "        return partdisjoin2(nums)"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "from typing import List\n",
    "import collections\n",
    "\n",
    "class Solution:\n",
    "    def partitionDisjoint(self, nums: list) -> int:\n",
    "        n = len(nums)\n",
    "        nums_sorted_idx = [(nums[ii], ii) for ii in range(n)]\n",
    "        nums_sorted_idx = sorted(nums_sorted_idx, key = lambda x: x[0])\n",
    "        max_count = -1\n",
    "        for ii in range(n):\n",
    "            max_count = max(max_count, nums_sorted_idx[ii][1])\n",
    "            if ii == max_count:\n",
    "                return max_count+1"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "from typing import List\n",
    "import collections\n",
    "\n",
    "class Solution:\n",
    "    def partitionDisjoint(self, nums: list) -> int:\n",
    "        n = len(nums)\n",
    "        nums_sorted_idx = [(nums[ii], ii) for ii in range(n)]\n",
    "        nums_sorted_idx = sorted(nums_sorted_idx, key = lambda x: x[0])\n",
    "        max_count = -1\n",
    "        for ii in range(n):\n",
    "            max_count = max(max_count, nums_sorted_idx[ii][1])\n",
    "            if ii == max_count:\n",
    "                return max_count+1"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "from typing import List\n",
    "import collections\n",
    "\n",
    "class Solution:\n",
    "    def partitionDisjoint(self, nums: list) -> int:\n",
    "        n = len(nums)\n",
    "        nums_sorted_idx = [(nums[ii], ii) for ii in range(n)]\n",
    "        nums_sorted_idx = sorted(nums_sorted_idx, key = lambda x: x[0])\n",
    "        max_count = -1\n",
    "        for ii in range(n):\n",
    "            max_count = max(max_count, nums_sorted_idx[ii][1])\n",
    "            if ii == max_count:\n",
    "                return max_count+1"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "from typing import List\n",
    "import collections\n",
    "\n",
    "class Solution:\n",
    "    def partitionDisjoint(self, nums: List[int]) -> int:\n",
    "        right_cnt = Counter(nums)\n",
    "        right_cnt = {k:v for k, v in sorted(right_cnt.items(), key=lambda x: x[0])}\n",
    "        left_cnt = defaultdict(int)\n",
    "        left_max = -1\n",
    "        for i in range(len(nums)):\n",
    "            left_cnt[nums[i]] += 1\n",
    "            right_cnt[nums[i]] -= 1\n",
    "            if right_cnt[nums[i]] == 0:\n",
    "                del right_cnt[nums[i]]\n",
    "            left_max = max(left_max, nums[i])\n",
    "            if left_max <= next(iter(right_cnt.items()))[0]:\n",
    "                break\n",
    "        return i + 1"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "from typing import List\n",
    "import collections\n",
    "\n",
    "class Solution:\n",
    "    def partitionDisjoint(self, nums: List[int]) -> int:\n",
    "        n=len(nums)\n",
    "        cnt=collections.defaultdict(int)\n",
    "        for i in range(n):\n",
    "            cnt[nums[i]]+=1\n",
    "        cnt=dict(sorted(cnt.items()))\n",
    "        # print(cnt)\n",
    "\n",
    "        left_max=nums[0]\n",
    "        right_min=min(nums)\n",
    "        left_len=0\n",
    "        for i in range(n):\n",
    "            a=nums[i]\n",
    "            # b=nums[i+1]\n",
    "            left_len+=1\n",
    "            left_max=a if a>left_max else left_max\n",
    "            cnt[a]-=1\n",
    "            if cnt[a]==0: \n",
    "                del cnt[a]\n",
    "            if a==right_min:\n",
    "                right_min=list(cnt.keys())[0]\n",
    "            # print(left_len,left_max,right_min)\n",
    "            # print(cnt)\n",
    "            if left_max<=right_min:\n",
    "                break\n",
    "\n",
    "        return left_len"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "from typing import List\n",
    "import collections\n",
    "\n",
    "class Solution:\n",
    "    def partitionDisjoint(self, nums: List[int]) -> int:\n",
    "        l = []\n",
    "        cp = 0\n",
    "        for i,n in enumerate(nums):\n",
    "            #print(i,n)\n",
    "            heapq.heappush(l, [n,i])\n",
    "        n,p = heapq.heappop(l)\n",
    "        if p==0:\n",
    "            return 1\n",
    "        else:\n",
    "            mx = p     \n",
    "            cp =0\n",
    "            #print(mx)\n",
    "            while mx>cp:\n",
    "                cp+=1\n",
    "                n,p = heapq.heappop(l) \n",
    "                mx = max(mx,p)  \n",
    "                #print(mx)\n",
    "            return mx+1"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "from typing import List\n",
    "import collections\n",
    "\n",
    "class Solution:\n",
    "    def partitionDisjoint(self, nums: List[int]) -> int:\n",
    "        nums_with_idx = [[nums[i], i]for i in range(len(nums))]\n",
    "        nums_with_idx.sort()\n",
    "        longest_idx = 0\n",
    "        for i in range(len(nums_with_idx)):\n",
    "            longest_idx = max(longest_idx, nums_with_idx[i][1])\n",
    "            if longest_idx <= i:\n",
    "                return longest_idx + 1\n",
    "        return longest_idx\n"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "from typing import List\n",
    "import collections\n",
    "\n",
    "class Solution:\n",
    "    def partitionDisjoint(self, nums: List[int]) -> int:\n",
    "        heap = []\n",
    "        left = nums[0]\n",
    "        for i, n in enumerate(nums):\n",
    "            heapq.heappush(heap, [n, i])\n",
    "        \n",
    "        res = 1\n",
    "        i = 0\n",
    "        while heap and heap[0][0] < left:\n",
    "\n",
    "            res = max(res, heapq.heappop(heap)[1] + 1)\n",
    "            while i < res:\n",
    "                left = max(left, nums[i])\n",
    "                i += 1\n",
    "        return res"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "from typing import List\n",
    "import collections\n",
    "\n",
    "class Solution:\n",
    "    def partitionDisjoint(self, nums: List[int]) -> int:\n",
    "        n = len(nums)\n",
    "\n",
    "        max_num = 0\n",
    "        min_num = 10**6\n",
    "\n",
    "        dict_lmax = {}\n",
    "        for i in range(n):\n",
    "            if nums[i] >= max_num:\n",
    "                max_num = nums[i]\n",
    "            dict_lmax[i] = max_num\n",
    "\n",
    "        flag = n - 1\n",
    "        for i in range(n-1,0,-1):\n",
    "            if nums[i] <= min_num:\n",
    "                min_num = nums[i]\n",
    "            if min_num >= dict_lmax[i-1]:\n",
    "                flag = i\n",
    "\n",
    "        return flag\n",
    "\n",
    "\n",
    "\n",
    "\n",
    "\n",
    "\n",
    "\n",
    "\n"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "from typing import List\n",
    "import collections\n",
    "\n",
    "\n",
    "class Solution:\n",
    "    def partitionDisjoint(self, nums: List[int]) -> int:\n",
    "        n = len(nums)\n",
    "        d = {}\n",
    "        d[n - 1] = nums[n - 1]\n",
    "        for i in range(n - 2, 0, -1):\n",
    "            d[i] = min(nums[i], d[i + 1])\n",
    "        max_val = nums[0]\n",
    "        for i in range(1, n):\n",
    "            if d[i] >= max_val:\n",
    "                return i\n",
    "            max_val = max(nums[i], max_val)\n",
    "        return 0\n"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "from typing import List\n",
    "import collections\n",
    "\n",
    "class Solution:\n",
    "    def partitionDisjoint(self, nums: List[int]) -> int:\n",
    "        a=[[nums[i],i] for i in range(len(nums))]\n",
    "        a=sorted(a,key = lambda x:x[0])\n",
    "        ans=0\n",
    "        for i in range(len(a)):\n",
    "            ans=max(ans,a[i][1])\n",
    "            if ans==i:\n",
    "                return i+1\n",
    "                "
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "from typing import List\n",
    "import collections\n",
    "\n",
    "class Solution:\n",
    "    def partitionDisjoint(self, nums: List[int]) -> int:\n",
    "        n = len(nums)\n",
    "        idx = list(sorted(zip(nums, [i for i in range(n)])))\n",
    "        print(idx)\n",
    "        ans = 0\n",
    "        pre_max = 0\n",
    "        for i in range(n):\n",
    "            pre_max = max(pre_max,idx[i][1])\n",
    "            if pre_max == i:\n",
    "                ans = i\n",
    "                break\n",
    "        return ans+1\n"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "from typing import List\n",
    "import collections\n",
    "\n",
    "class BIT:\n",
    "    def __init__(self, n: int):\n",
    "        self.n = n\n",
    "        self.tree = [0] * (n + 1)\n",
    "\n",
    "    @staticmethod\n",
    "    def lowbit(x: int) -> int:\n",
    "        return x & (-x)\n",
    "\n",
    "    def update(self, x: int, v: int = 1):\n",
    "        while x <= self.n:\n",
    "            self.tree[x] += v\n",
    "            x += BIT.lowbit(x)\n",
    "\n",
    "    def query(self, x: int) -> int:\n",
    "        ans = 0\n",
    "        while x > 0:\n",
    "            ans += self.tree[x]\n",
    "            x -= BIT.lowbit(x)\n",
    "        return ans\n",
    "\n",
    "    def queryRange(self, x: int, y: int) -> int:\n",
    "        return self.query(y) - self.query(x - 1)\n",
    "\n",
    "class Solution:\n",
    "    def partitionDisjoint(self, nums: List[int]) -> int:\n",
    "        n, m = 0, len(nums)\n",
    "        for i, x in enumerate(nums):\n",
    "            nums[i] += 1\n",
    "            n = max(n, nums[i])\n",
    "        \n",
    "        b = BIT(n)\n",
    "        for x in nums:\n",
    "            b.update(x)\n",
    "        \n",
    "        mx = -1\n",
    "        for i, x in enumerate(nums, 1):\n",
    "            mx = max(mx, x)\n",
    "            b.update(x, -1)\n",
    "            if b.queryRange(mx, n) == m - i:\n",
    "                return i\n",
    "        \n",
    "        return -1\n",
    "\n"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "from typing import List\n",
    "import collections\n",
    "\n",
    "import numpy as np\n",
    "class Solution:\n",
    "    def partitionDisjoint(self, A: List[int]) -> int:\n",
    "        idx =np.argmin(A)\n",
    "        print(idx)\n",
    "        #left = []\n",
    "        left = [A[i] for i in range(idx+1)]\n",
    "        l_max = max(A[:idx+1])\n",
    "        count = idx + 1\n",
    "        right = idx + 1\n",
    "        r_min = min(A[right:])\n",
    "        if right == len(A):\n",
    "            return right\n",
    "        while l_max > r_min:\n",
    "            element = A[right]\n",
    "            right += 1\n",
    "            count += 1\n",
    "            if element > l_max:\n",
    "                l_max = element\n",
    "            r_min = min(A[right:])\n",
    "        return count\n",
    "\n"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "from typing import List\n",
    "import collections\n",
    "\n",
    "import numpy as np\n",
    "class Solution:\n",
    "    def partitionDisjoint(self, A: List[int]) -> int:\n",
    "        idx =np.argmin(A)\n",
    "        print(idx)\n",
    "        left = []\n",
    "        left = [A[i] for i in range(idx+1)]\n",
    "        l_max = max(left)\n",
    "        count = len(left)\n",
    "        right = [A[i] for i in range(idx+1,len(A))]\n",
    "        if right == []:\n",
    "            return len(A)\n",
    "        while l_max > min(right):\n",
    "            element = right.pop(0)\n",
    "            count += 1\n",
    "            if element > l_max:\n",
    "                l_max = element\n",
    "        return count\n",
    "\n"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "from typing import List\n",
    "import collections\n",
    "\n",
    "import numpy as np\n",
    "class Solution:\n",
    "    def partitionDisjoint(self, A: List[int]) -> int:\n",
    "        # idx =np.argmin(A)\n",
    "        # print(idx)\n",
    "        # #left = []\n",
    "        # left = [A[i] for i in range(idx+1)]\n",
    "        # l_max = max(A[:idx+1])\n",
    "        # count = idx + 1\n",
    "        # right = idx + 1\n",
    "        # r_min = min(A[right:])\n",
    "        # if right == len(A):\n",
    "        #     return right\n",
    "        # while l_max > r_min:\n",
    "        #     element = A[right]\n",
    "        #     right += 1\n",
    "        #     count += 1\n",
    "        #     if element > l_max:\n",
    "        #         l_max = element\n",
    "        #     r_min = min(A[right:])\n",
    "        # return count\n",
    "\n",
    "\n",
    "        n = len(A)\n",
    "        l_max = [0] * n\n",
    "        r_min = [0] * n\n",
    "        l = A[0]\n",
    "        for i in range(0, n):\n",
    "            l = max(l, A[i])\n",
    "            l_max[i] = l\n",
    "        \n",
    "        r = A[-1]\n",
    "        for i in range(n-1, -1, -1):\n",
    "            r = min(r, A[i])\n",
    "            r_min[i] = r\n",
    "        \n",
    "        for i in range(n-1):\n",
    "            if l_max[i] <= r_min[i+1]:\n",
    "                return i+1\n",
    "\n"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "from typing import List\n",
    "import collections\n",
    "\n",
    "class Solution:\n",
    "    def partitionDisjoint(self, nums: List[int]) -> int:\n",
    "        q = [[nums[i], i] for i in range(len(nums))]\n",
    "        heapq.heapify(q)\n",
    "        mi = nums[0]\n",
    "        for i in range(len(nums)-1):\n",
    "            while q[0][1]<=i:\n",
    "                heapq.heappop(q)\n",
    "            if mi<=q[0][0]:\n",
    "                return i+1\n",
    "            mi = max(mi, nums[i+1])\n",
    "        return -1\n",
    "        "
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "from typing import List\n",
    "import collections\n",
    "\n",
    "class Solution:\n",
    "    def partitionDisjoint(self, nums: List[int]) -> int:\n",
    "        max = nums[0] \n",
    "        max_min_list = [[max]]\n",
    "        for n in nums[1:]:\n",
    "            if n > max:\n",
    "                max = n\n",
    "            max_min_list.append([max])\n",
    "        ln = len(nums)\n",
    "        min = nums[ln-1]\n",
    "        max_min_list[ln-2].append(min)\n",
    "        for i in range(2, ln):\n",
    "            if nums[ln-i] < min:\n",
    "                min = nums[ln-i]\n",
    "            max_min_list[ln-i-1].append(min)\n",
    "        for i, (max, min) in enumerate(max_min_list):\n",
    "            if max <= min:\n",
    "                return i +1\n",
    "        return 0"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "from typing import List\n",
    "import collections\n",
    "\n",
    "class Solution:\n",
    "    def partitionDisjoint(self, nums: List[int]) -> int:\n",
    "        n = len(nums)\n",
    "        p = list(enumerate(nums))\n",
    "        p.sort(key=lambda x : x[1])\n",
    "        print(p)\n",
    "        idx = p[0][0]\n",
    "        max_num = max(nums[:idx + 1])\n",
    "        temp = n + 1\n",
    "        for i in range(p[0][0] + 1, n):\n",
    "            if nums[i] < max_num:\n",
    "                idx = i\n",
    "                if temp < i:\n",
    "                    max_num = nums[temp]\n",
    "            else:\n",
    "                temp = i\n",
    "        return idx + 1\n",
    "        "
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "from typing import List\n",
    "import collections\n",
    "\n",
    "class Solution:\n",
    "    def partitionDisjoint(self, nums: List[int]) -> int:\n",
    "        max_min = [[-math.inf, math.inf] for _ in range(len(nums))]\n",
    "        _max = -math.inf\n",
    "        _min = math.inf\n",
    "        for i in range(len(nums)):\n",
    "            _max = max(nums[i], _max)\n",
    "            max_min[i][0] = _max\n",
    "        for i in range(len(nums) - 1, -1, -1):\n",
    "            _min = min(nums[i], _min)\n",
    "            max_min[i][1] = _min\n",
    "\n",
    "        for i in range(len(nums) - 1):\n",
    "            if max_min[i][0] <= max_min[i + 1][1]:\n",
    "                return i + 1"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "from typing import List\n",
    "import collections\n",
    "\n",
    "class Solution:\n",
    "    def canThreePartsEqualSum(self, arr: List[int]) -> bool:\n",
    "        partition_sum = sum(arr) / 3\n",
    "        cur_p_sum = 0\n",
    "        flags = []\n",
    "        for each_num in arr:\n",
    "            cur_p_sum += each_num\n",
    "            if cur_p_sum == partition_sum:\n",
    "                cur_p_sum = 0\n",
    "                flags.append(True)\n",
    "        return len(flags) >= 3\n"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "from typing import List\n",
    "import collections\n",
    "\n",
    "# https://leetcode.cn/problems/partition-array-into-three-parts-with-equal-sum/\n",
    "from typing import List\n",
    "\n",
    "\n",
    "class Solution:\n",
    "    def canThreePartsEqualSum(self, arr: List[int]) -> bool:\n",
    "        if arr.__len__() < 3:\n",
    "            return False\n",
    "        sm = sum(arr)\n",
    "        # print(\"sm=\", sm)\n",
    "        if sm % 3 != 0:\n",
    "            return False\n",
    "        counter = 0\n",
    "        tmp = 0\n",
    "        for num in arr:\n",
    "            tmp += num\n",
    "            if tmp == sm/3:\n",
    "                counter += 1\n",
    "                tmp = 0\n",
    "        return counter >= 3"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "from typing import List\n",
    "import collections\n",
    "\n",
    "class Solution:\n",
    "    def partitionArray(self, nums: List[int], k: int) -> int:\n",
    "        nums.sort()\n",
    "        n = len(nums)\n",
    "        ans = i = 0\n",
    "        while i < n:\n",
    "            j = i\n",
    "            while j+1 < n and nums[j+1] - nums[i] <= k:\n",
    "                j += 1\n",
    "            ans += 1\n",
    "            i = j+1\n",
    "        return ans"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "from typing import List\n",
    "import collections\n",
    "\n",
    "class Solution:\n",
    "    def partitionArray(self, nums: List[int], k: int) -> int:\n",
    "        nums.sort()\n",
    "        result = 1\n",
    "        last = nums[0]\n",
    "        for num in nums:\n",
    "            if num - last > k:\n",
    "                last = num\n",
    "                result += 1\n",
    "        return result\n",
    "\n",
    "\n",
    "\n",
    "\n",
    "\n",
    "\n",
    "\n",
    "\n",
    "            \n",
    "        \n",
    "\n",
    "           \n"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "from typing import List\n",
    "import collections\n",
    "\n",
    "class Solution:\n",
    "    def partitionArray(self, nums: List[int], k: int) -> int:\n",
    "        nums.sort()\n",
    "        ans = 0\n",
    "        cur = 0\n",
    "        n = len(nums)\n",
    "        while cur < n:\n",
    "            cur = bisect_right(nums, nums[cur] + k)\n",
    "            ans += 1\n",
    "        return ans\n"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "from typing import List\n",
    "import collections\n",
    "\n",
    "class Solution:\n",
    "    def partitionArray(self, nums: List[int], k: int, res = 0, cur = -123456) -> int:\n",
    "        for x in sorted(nums):\n",
    "            if x - cur > k: cur, res = x, res + 1\n",
    "        return res"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "from typing import List\n",
    "import collections\n",
    "\n",
    "class Solution:\n",
    "    def partitionArray(self, nums: List[int], k: int) -> int:\n",
    "        nums.sort()\n",
    "        res = 1\n",
    "        pre_val = nums[0]\n",
    "        for val in nums:\n",
    "            if val-pre_val>k:\n",
    "                res += 1\n",
    "                pre_val = val \n",
    "        return res"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "from typing import List\n",
    "import collections\n",
    "\n",
    "class Solution:\n",
    "    def partitionArray(self, nums: List[int], k: int) -> int:\n",
    "        n = len(nums)\n",
    "        nums.sort()\n",
    "        ans = 0\n",
    "        l = 0\n",
    "        r = 0\n",
    "        while l < n:\n",
    "            while r < n and nums[r] - nums[l] <= k:\n",
    "                r += 1\n",
    "            ans += 1\n",
    "            l = r\n",
    "        return ans\n",
    "            "
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "from typing import List\n",
    "import collections\n",
    "\n",
    "class Solution:\n",
    "    def partitionArray(self, nums: List[int], k: int) -> int:\n",
    "        nums.sort()\n",
    "        result = 1\n",
    "        last = nums[0]\n",
    "        for num in nums:\n",
    "            if num - last > k:\n",
    "                last = num\n",
    "                result += 1\n",
    "        return result\n"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "from typing import List\n",
    "import collections\n",
    "\n",
    "class Solution:\n",
    "    def partitionArray(self, nums: List[int], k: int) -> int:\n",
    "        nums.sort()\n",
    "        start = nums[0]\n",
    "        ans = 0\n",
    "        for num in nums[1:]:\n",
    "            if num - start > k:\n",
    "                start = num\n",
    "                ans += 1\n",
    "        return ans+1"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "from typing import List\n",
    "import collections\n",
    "\n",
    "class Solution:\n",
    "    def partitionArray(self, nums: list[int], k: int) -> int:\n",
    "        def test(target):\n",
    "            tot=0\n",
    "            p=0\n",
    "            while p<len(nums):\n",
    "                left=0\n",
    "                right = len(nums)-1\n",
    "                while left<right:\n",
    "                    mid = (left+right)//2+1\n",
    "                    if nums[mid]-nums[p]>k:\n",
    "                        right=mid-1\n",
    "                    else:\n",
    "                        left=mid\n",
    "                p=left+1\n",
    "                tot+=1\n",
    "            return tot<=target\n",
    "        nums.sort()\n",
    "        left=1\n",
    "        right=len(nums)\n",
    "        while left<right:\n",
    "            mid = (left+right)//2\n",
    "            if test(mid):\n",
    "                right=mid\n",
    "            else:\n",
    "                left=mid+1\n",
    "        return left"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "from typing import List\n",
    "import collections\n",
    "\n",
    "class Solution:\n",
    "    def partitionArray(self, nums: List[int], k: int) -> int:\n",
    "        nums.sort()\n",
    "        cnt = 1\n",
    "        min_num = nums[0]\n",
    "        for i in range(1, len(nums)):\n",
    "            if nums[i] - min_num > k:\n",
    "                cnt += 1\n",
    "                min_num = nums[i]\n",
    "        return cnt"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "from typing import List\n",
    "import collections\n",
    "\n",
    "class Solution:\n",
    "    def partitionArray(self, nums: List[int], k: int) -> int:\n",
    "        nums.sort()\n",
    "        result = 1\n",
    "        last = nums[0]\n",
    "        for num in nums:\n",
    "            if num - last > k:\n",
    "                last = num\n",
    "                result += 1\n",
    "        return result\n"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "from typing import List\n",
    "import collections\n",
    "\n",
    "class Solution:\n",
    "    def partitionArray(self, nums: List[int], k: int) -> int:\n",
    "        nums.sort()\n",
    "        ans = 0\n",
    "        n = len(nums)\n",
    "        res = nums[0]\n",
    "        for i in range(1,n):\n",
    "            if nums[i] - res <= k:\n",
    "                continue\n",
    "            else:\n",
    "                res = nums[i]\n",
    "                ans += 1\n",
    "        return ans + 1"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "from typing import List\n",
    "import collections\n",
    "\n",
    "class Solution:\n",
    "    def partitionArray(self, nums: List[int], k: int) -> int:\n",
    "        nums.sort()\n",
    "        result = 0\n",
    "        left, right = 0, 0\n",
    "        result = 1\n",
    "        while(right < len(nums)):\n",
    "            if(nums[right] - nums[left] > k):\n",
    "                left = right      \n",
    "                result += 1 \n",
    "            right += 1\n",
    "        return result"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "from typing import List\n",
    "import collections\n",
    "\n",
    "class Solution:\n",
    "    def partitionArray(self, nums: List[int], k: int) -> int:\n",
    "        nums.sort()\n",
    "        l = float('-inf')\n",
    "        result = 0\n",
    "        for n in nums:\n",
    "            if n - l > k:\n",
    "                l = n\n",
    "                result += 1\n",
    "        return result\n"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "from typing import List\n",
    "import collections\n",
    "\n",
    "class Solution:\n",
    "    def partitionArray(self, nums: List[int], k: int) -> int:\n",
    "        nums.sort();ans,x=1,nums[0]\n",
    "        for i in nums:\n",
    "            if(i-x<=k):continue\n",
    "            else:ans,x=ans+1,i\n",
    "        return ans"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "from typing import List\n",
    "import collections\n",
    "\n",
    "class Solution:\n",
    "    def partitionArray(self, nums: List[int], k: int) -> int:\n",
    "        # 先排序\n",
    "        nums.sort()\n",
    "        count = len(nums)\n",
    "\n",
    "        _min = nums[0]\n",
    "        result = 1\n",
    "        for i in range(1, count):\n",
    "            if nums[i] - _min > k:\n",
    "                result += 1\n",
    "                _min = nums[i]\n",
    "        return result\n",
    "\n"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "from typing import List\n",
    "import collections\n",
    "\n",
    "class Solution:\n",
    "    def partitionArray(self, nums: List[int], k: int) -> int:\n",
    "        nums.sort()\n",
    "        ans = 1\n",
    "        pre =nums[0]\n",
    "        for num in nums[1:]:\n",
    "            if num <= pre+k:\n",
    "                continue\n",
    "            else:\n",
    "                ans += 1\n",
    "                pre = num\n",
    "        return ans\n"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "from typing import List\n",
    "import collections\n",
    "\n",
    "class Solution:\n",
    "    def partitionArray(self, nums: List[int], k: int) -> int:\n",
    "        nums.sort()\n",
    "        n=len(nums)\n",
    "        ans=1\n",
    "        i=nums[0]\n",
    "        for j in range(n):\n",
    "            if nums[j]-i>k:\n",
    "                i=nums[j]\n",
    "                ans+=1\n",
    "        return ans"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "from typing import List\n",
    "import collections\n",
    "\n",
    "class Solution:\n",
    "    def partitionArray(self, nums: List[int], k: int) -> int:\n",
    "        nums.sort()\n",
    "        result = 1\n",
    "        last = nums[0]\n",
    "        for num in nums:\n",
    "            if num - last > k:\n",
    "                last = num\n",
    "                result += 1\n",
    "        return result\n"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "from typing import List\n",
    "import collections\n",
    "\n",
    "class Solution:\n",
    "    def partitionArray(self, nums: List[int], k: int) -> int:\n",
    "        n = len(nums)\n",
    "        nums.sort()\n",
    "        ans = 1\n",
    "        t = nums[0]\n",
    "        for i in range(1, n):\n",
    "            if nums[i] - t > k:\n",
    "                t = nums[i]\n",
    "                ans += 1\n",
    "\n",
    "        return ans"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "from typing import List\n",
    "import collections\n",
    "\n",
    "class Solution:\n",
    "    def partitionArray(self, nums: List[int], k: int) -> int:\n",
    "        nums.sort()\n",
    "\n",
    "        cnt=1\n",
    "        l=nums[0]\n",
    "        r=nums[0]+k\n",
    "        \n",
    "        for i,v in enumerate(nums):\n",
    "            if v >r:\n",
    "                l=v\n",
    "                r=v+k\n",
    "                cnt+=1\n",
    "        \n",
    "        return cnt"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "from typing import List\n",
    "import collections\n",
    "\n",
    "class Solution:\n",
    "    def partitionArray(self, nums: List[int], k: int) -> int:\n",
    "        nums.sort()\n",
    "        ans = 1\n",
    "        pre = nums[0]\n",
    "        for x in nums[1:]:\n",
    "            if x - pre > k:\n",
    "                ans += 1\n",
    "                pre = x\n",
    "        return ans"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "from typing import List\n",
    "import collections\n",
    "\n",
    "class Solution:\n",
    "    def partitionArray(self, nums: List[int], k: int) -> int:\n",
    "        nums.sort()\n",
    "        m = nums[0]\n",
    "        ret = 1\n",
    "        for x in nums[1:]:\n",
    "            if x - m > k:\n",
    "                ret += 1\n",
    "                m = x\n",
    "        return ret"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "from typing import List\n",
    "import collections\n",
    "\n",
    "class Solution:\n",
    "    def partitionArray(self, nums: List[int], k: int) -> int:\n",
    "        r = 1\n",
    "        nums = sorted(nums)\n",
    "        \n",
    "        if len(nums) == 1:\n",
    "            return 1\n",
    "        cur_big = nums[0]\n",
    "        cur_sml = nums[0]\n",
    "        for n in nums:\n",
    "            print(n)\n",
    "            cur_big = max(cur_big, n)\n",
    "            cur_sml = min(cur_sml, n)\n",
    "            if cur_big - cur_sml > k:\n",
    "                r += 1\n",
    "                cur_big = n\n",
    "                cur_sml = n\n",
    "        return r\n"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "from typing import List\n",
    "import collections\n",
    "\n",
    "class Solution:\n",
    "    def partitionArray(self, nums: List[int], k: int) -> int:\n",
    "        ans=0\n",
    "        nums.sort()\n",
    "        p=-inf \n",
    "        for x in nums:\n",
    "            if x-p>k:\n",
    "                ans+=1\n",
    "                p=x\n",
    "        return ans"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "from typing import List\n",
    "import collections\n",
    "\n",
    "class Solution:\n",
    "    def partitionArray(self, nums: List[int], k: int) -> int:\n",
    "\n",
    "        nums.sort()\n",
    "        start = True\n",
    "        cur_min = nums[0]\n",
    "        res = 1\n",
    "        for num in nums[1:]:\n",
    "            if num>cur_min+k:\n",
    "                res+=1\n",
    "                cur_min = num\n",
    "        return res\n",
    "            \n",
    "                "
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "from typing import List\n",
    "import collections\n",
    "\n",
    "class Solution:\n",
    "    def partitionArray(self, nums: List[int], k: int) -> int:\n",
    "        nums.sort()\n",
    "        res = 1\n",
    "        tgt = nums[0]\n",
    "        for n in nums:\n",
    "            if n - tgt > k:\n",
    "                res += 1\n",
    "                tgt = n\n",
    "        return res"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "from typing import List\n",
    "import collections\n",
    "\n",
    "class Solution:\n",
    "    def partitionArray(self, nums: list[int], k: int) -> int:\n",
    "        def test():\n",
    "            tot=0\n",
    "            p=0\n",
    "            while p<len(nums):\n",
    "                left=0\n",
    "                right = len(nums)-1\n",
    "                while left<right:\n",
    "                    mid = (left+right)//2+1\n",
    "                    if nums[mid]-nums[p]>k:\n",
    "                        right=mid-1\n",
    "                    else:\n",
    "                        left=mid\n",
    "                p=left+1\n",
    "                tot+=1\n",
    "            return tot\n",
    "        nums.sort()\n",
    "        return test()"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "from typing import List\n",
    "import collections\n",
    "\n",
    "class Solution:\n",
    "    def partitionArray(self, nums: List[int], k: int) -> int:\n",
    "        nums.sort()\n",
    "        pre = nums[0]\n",
    "        ans = 0\n",
    "        for i in range(1, len(nums)):\n",
    "            if nums[i] - pre > k:\n",
    "                ans += 1\n",
    "                pre = nums[i]\n",
    "        return ans + 1"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "from typing import List\n",
    "import collections\n",
    "\n",
    "class Solution:\n",
    "    def partitionArray(self, nums: list[int], k: int) -> int:\n",
    "        def test(target):\n",
    "            list1 = nums.copy()\n",
    "            tot=0\n",
    "            p=0\n",
    "            while p<len(list1):\n",
    "                left=0\n",
    "                right = len(list1)-1\n",
    "                while left<right:\n",
    "                    mid = (left+right)//2+1\n",
    "                    if list1[mid]-list1[p]>k:\n",
    "                        right=mid-1\n",
    "                    else:\n",
    "                        left=mid\n",
    "                p=left+1\n",
    "                tot+=1\n",
    "            return tot<=target\n",
    "        nums.sort()\n",
    "        left=1\n",
    "        right=len(nums)\n",
    "        while left<right:\n",
    "            mid = (left+right)//2\n",
    "            if test(mid):\n",
    "                right=mid\n",
    "            else:\n",
    "                left=mid+1\n",
    "        return left"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "from typing import List\n",
    "import collections\n",
    "\n",
    "class Solution:\n",
    "    def partitionArray(self, nums: List[int], k: int) -> int:\n",
    "        # 先排序\n",
    "        nums.sort()\n",
    "        count = len(nums)\n",
    "\n",
    "        _min = nums[0]\n",
    "        _num = _min + k\n",
    "        result = 1\n",
    "        for i in range(1, count):\n",
    "            if nums[i] > _num:\n",
    "                result += 1\n",
    "                _min = nums[i]\n",
    "                _num = _min + k\n",
    "        return result\n",
    "\n"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "from typing import List\n",
    "import collections\n",
    "\n",
    "class Solution:\n",
    "    def partitionArray(self, nums: List[int], k: int) -> int:\n",
    "        nums.sort()\n",
    "        result = 0\n",
    "        left, right = 0, 0\n",
    "        result = 1\n",
    "        while(right < len(nums)):\n",
    "            if(nums[right] - nums[left] > k):\n",
    "                left = right      \n",
    "                result += 1 \n",
    "            right += 1\n",
    "        return result"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "from typing import List\n",
    "import collections\n",
    "\n",
    "class Solution:\n",
    "    def partitionArray(self, nums: List[int], k: int) -> int:\n",
    "        nums.sort()\n",
    "        partitions = 1\n",
    "        min_val = nums[0]\n",
    "        max_val = nums[0]\n",
    "\n",
    "        for num in nums:\n",
    "            if num - min_val > k or max_val - num > k:\n",
    "                partitions += 1\n",
    "                min_val = num\n",
    "                max_val = num\n",
    "            else:\n",
    "                max_val = max(max_val, num)\n",
    "\n",
    "        return partitions"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "from typing import List\n",
    "import collections\n",
    "\n",
    "class Solution:\n",
    "    def partitionArray(self, nums: List[int], k: int) -> int:\n",
    "        c = list(set(nums))\n",
    "        c.sort()\n",
    "        n = len(c)\n",
    "        result = 0\n",
    "        i = 0\n",
    "        while i < n:\n",
    "            min_value = c[i]\n",
    "            j = i + 1\n",
    "            while j < n and c[j] - c[i] <= k:\n",
    "                j += 1\n",
    "            result += 1\n",
    "            i = j\n",
    "        return result"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "from typing import List\n",
    "import collections\n",
    "\n",
    "class Solution:\n",
    "    def canPartition(self, nums: List[int]) -> bool:\n",
    "        total = sum(nums)\n",
    "        if total % 2 == 1:\n",
    "            return False\n",
    "        partitionSum = total // 2\n",
    "        # problem becomes wheather we can find a subset of nums such that they sum up to partitionSum\n",
    "        # reference: https://leetcode.com/problems/partition-equal-subset-sum/solutions/90592/0-1-knapsack-detailed-explanation/?envType=study-plan&id=level-2\n",
    "        # as in 2D array solution, each time when expanding subset from nums[:i] to nums[:i+1]\n",
    "        # the solution only depends on previous row, so means we only need to keep 1D array\n",
    "        # representing the row in the 2D array solution and modify it in place\n",
    "        dp = [False for i in range(partitionSum+1)]\n",
    "        dp[0] = True\n",
    "        for num in nums:\n",
    "            for j in range(partitionSum,num-1,-1):\n",
    "                dp[j] = dp[j] or dp[j-num]\n",
    "        return dp[partitionSum]"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "from typing import List\n",
    "import collections\n",
    "\n",
    "class Solution:\n",
    "    def canPartition(self, nums: List[int]) -> bool:    \n",
    "        def try_partition(nums, index, capacity):\n",
    "            if capacity == 0:\n",
    "                return True\n",
    "            if index < 0 or capacity < 0:\n",
    "                return False\n",
    "            if memo[index][capacity] != -1:\n",
    "                return memo[index][capacity] == 1\n",
    "            memo[index][capacity] = 1 if try_partition(nums, index-1, capacity) or try_partition(nums, index-1, capacity-nums[index]) else 0\n",
    "            return memo[index][capacity] == 1\n",
    "        capacity = 0\n",
    "        n = len(nums)\n",
    "        for i in range(n):\n",
    "            capacity += nums[i]\n",
    "        if capacity % 2 != 0:\n",
    "            return False\n",
    "        memo = [[-1]*(capacity//2+1) for _ in range(n)]\n",
    "        return try_partition(nums, n-1, capacity//2)"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "from typing import List\n",
    "import collections\n",
    "\n",
    "from typing import List\n",
    "\n",
    "\n",
    "class Solution:\n",
    "    def partitionLabels(self, s: str) -> List[int]:\n",
    "        ans = []\n",
    "        start = end = 0\n",
    "        for i in range(len(s)):\n",
    "            index = s.rfind(s[i])\n",
    "            if index + 1 > end:\n",
    "                end = index + 1\n",
    "\n",
    "            if end >= len(s):\n",
    "                ans.append(end - start)\n",
    "                return ans\n",
    "\n",
    "            if i >= end - 1:\n",
    "                ans.append(end - start)\n",
    "                start = end\n",
    "        return [len(s)]"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "from typing import List\n",
    "import collections\n",
    "\n",
    "class Solution(object):\n",
    "    def partitionLabels(self, S):\n",
    "        \"\"\"\n",
    "        :type S: str\n",
    "        :rtype: List[int]\n",
    "        \"\"\"\n",
    "        lindex = {c: i for i, c in enumerate(S)}\n",
    "        j = anchor = 0\n",
    "        ans = []\n",
    "        for i, c in enumerate(S):\n",
    "            j = max(j, lindex[c])\n",
    "            if i == j:\n",
    "                ans.append(j - anchor + 1)\n",
    "                anchor = j + 1\n",
    "        return ans\n"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "from typing import List\n",
    "import collections\n",
    "\n",
    "class Solution:\n",
    "    def partitionLabels(self, S):\n",
    "        \"\"\"\n",
    "        :type S: str\n",
    "        :rtype: List[int]\n",
    "        \"\"\"\n",
    "        #思路计算每个字母最开始和最后出现的位置，得到一个区间序列，然后按照合并重复区间的方法\n",
    "        #得到合并完成的序列，则每个子序列的长度即为每个字符串片段的长度\n",
    "        data = []\n",
    "        for ch in set(S):\n",
    "            data.append(self.findFirstandLast(ch, S))\n",
    "        return [l[1]-l[0]+1 for l in self.mergeInterval(data)]\n",
    "        \n",
    "    def findFirstandLast(self, ch, S):\n",
    "        start = 0\n",
    "        end = 0\n",
    "        for i in range(len(S)):\n",
    "            if S[i] == ch:\n",
    "                start = i\n",
    "                break\n",
    "        for i in range(len(S)-1,-1,-1):\n",
    "            if S[i] == ch:\n",
    "                end = i\n",
    "                break\n",
    "        return [start, end]\n",
    "        \n",
    "              \n",
    "    def mergeInterval(self, intervals):\n",
    "        intervals = sorted(intervals)\n",
    "        i = 0\n",
    "        while i < len(intervals)-1:\n",
    "            if intervals[i+1][1] <= intervals[i][1]:\n",
    "                intervals.pop(i+1)\n",
    "            elif intervals[i+1][0] <= intervals[i][1]:\n",
    "                intervals[i][1] = intervals[i+1][1]\n",
    "                intervals.pop(i+1)\n",
    "            else:\n",
    "                i+=1\n",
    "        return intervals\n",
    "        "
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "from typing import List\n",
    "import collections\n",
    "\n",
    "class Solution:\n",
    "    def partitionLabels(self, S):\n",
    "        \"\"\"\n",
    "        :type S: str\n",
    "        :rtype: List[int]\n",
    "        \"\"\"\n",
    "        index_dict = {}\n",
    "        result = []\n",
    "        for i in range(len(S)):\n",
    "            if S[i] in index_dict.keys():\n",
    "                index_dict[S[i]].append(i)\n",
    "            else: index_dict[S[i]] = [i]\n",
    "\n",
    "        index = 0\n",
    "        while index < len(S):\n",
    "            init_range = [index_dict[S[index]][0], index_dict[S[index]][-1]]\n",
    "            i = init_range[0]\n",
    "            while i in range(init_range[0], init_range[-1]):\n",
    "                if index_dict[S[i]][-1] > init_range[-1]: init_range[-1] = index_dict[S[i]][-1]\n",
    "                i += 1\n",
    "            index = init_range[-1] + 1\n",
    "            result.append(init_range[-1] - init_range[0] + 1)\n",
    "\n",
    "        return result"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "from typing import List\n",
    "import collections\n",
    "\n",
    "class Solution:\n",
    "    def partitionLabels(self, S):\n",
    "        \"\"\"\n",
    "        :type S: str\n",
    "        :rtype: List[int]\n",
    "        \"\"\"\n",
    "        c_max_index = {}#记录每个字符出现的最大位置\n",
    "        n = len(S)\n",
    "        now_max_index = 0#记录当前扫描的字符串中字符的最大位置\n",
    "        l = 0 #当前扫描字符串的开始位置\n",
    "        res = []\n",
    "        for i in range(n):\n",
    "            c_max_index[S[i]] = i\n",
    "        for i in range(n):\n",
    "            now_max_index = max(now_max_index, c_max_index[S[i]])\n",
    "            if i == now_max_index:\n",
    "                res.append(i-l+1)\n",
    "                l = i+1\n",
    "                now_max_index = 0\n",
    "        \n",
    "        return res\n",
    "                \n",
    "            "
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "from typing import List\n",
    "import collections\n",
    "\n",
    "class Solution:\n",
    "    def partitionLabels(self, S):\n",
    "        \"\"\"\n",
    "        :type S: str\n",
    "        :rtype: List[int]\n",
    "        \"\"\"\n",
    "        res=[]\n",
    "        vec=[]\n",
    "        for i in range(0,26):\n",
    "            vec.append(0)\n",
    "        last = 0\n",
    "        for i in range(0,len(S)):\n",
    "            vec[ord(S[i])-ord('a')] += 1\n",
    "        st = set()\n",
    "        for i in range(0,len(S)):\n",
    "            st.add(S[i])\n",
    "            vec[ord(S[i])-ord('a')] -= 1\n",
    "            if vec[ord(S[i])-ord('a')]==0:\n",
    "                if S[i] in st:\n",
    "                    st.remove(S[i])\n",
    "                if st==set():\n",
    "                    res.append(i-last+1)\n",
    "                    last=i+1\n",
    "        return res"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "from typing import List\n",
    "import collections\n",
    "\n",
    "class Solution:\n",
    "    def partitionLabels(self, S):\n",
    "        \"\"\"\n",
    "        :type S: str\n",
    "        :rtype: List[int]\n",
    "        \"\"\"\n",
    "        lastIndexOfChar={}\n",
    "        for i in range(len(S)):\n",
    "            lastIndexOfChar[S[i]]=i\n",
    "        \n",
    "        firstindex=0\n",
    "        partions=[]\n",
    "        while firstindex<len(S):\n",
    "            lastindex = firstindex\n",
    "            i=firstindex\n",
    "            while i<=lastindex:\n",
    "                if lastIndexOfChar[S[i]]>lastindex:\n",
    "                    lastindex = lastIndexOfChar[S[i]]\n",
    "                i+=1\n",
    "            partions.append(lastindex-firstindex+1)\n",
    "            firstindex = lastindex+1\n",
    "        return partions\n",
    "    def char2Index(self,c):\n",
    "        return c-\"a\"\n",
    "        "
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "from typing import List\n",
    "import collections\n",
    "\n",
    "class Solution:\n",
    "    def partitionLabels(self, S: 'str') -> 'List[int]':\n",
    "        i = 0\n",
    "        ans = []\n",
    "        while i < len(S):\n",
    "            j = S.rfind(S[i])\n",
    "            m = j\n",
    "            k = i + 1\n",
    "            while k < m:\n",
    "                m = max(m, S.rfind(S[k]))\n",
    "                k += 1\n",
    "            m += 1\n",
    "            ans.append(m - i)\n",
    "            i = m\n",
    "        return ans\n"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "from typing import List\n",
    "import collections\n",
    "\n",
    "class Solution:\n",
    "    def partitionLabels(self, S: str) -> List[int]:\n",
    "        dic={}\n",
    "        for i in range(len(S)):\n",
    "            if S[i] not in dic:\n",
    "                dic[S[i]]=[i,i]\n",
    "            else:\n",
    "                dic[S[i]][1]=i\n",
    "        weizhi1=0\n",
    "        weizhi2=dic[S[0]][1]\n",
    "\n",
    "        ans=[]\n",
    "        i=1\n",
    "        while weizhi2<len(S):\n",
    "            while i<=weizhi2:\n",
    "                weizhi2=max(weizhi2,dic[S[i]][1])\n",
    "                i+=1\n",
    "            if weizhi2+1>=len(S):\n",
    "                ans.append(len(S)-weizhi1)\n",
    "                break\n",
    "            else:\n",
    "                ans.append(weizhi2-weizhi1+1)\n",
    "            weizhi1,weizhi2=weizhi2+1,dic[S[weizhi2+1]][1]\n",
    "        return ans\n",
    "        \n",
    "\n"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "from typing import List\n",
    "import collections\n",
    "\n",
    "class Solution:\n",
    "    def partitionLabels(self, S: str) -> List[int]:\n",
    "        dic= {}\n",
    "        for idx, cha in enumerate(S):\n",
    "            dic[cha] = idx\n",
    "        result = []\n",
    "        cur = dic[S[0]]\n",
    "        for i, c in enumerate(S):\n",
    "            if dic[c] > cur:\n",
    "                cur = dic[c]\n",
    "            if i == cur:\n",
    "                result.append(cur+1-sum(result))\n",
    "        return result"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "from typing import List\n",
    "import collections\n",
    "\n",
    "class Solution:\n",
    "    def partitionLabels(self, S: str) -> List[int]:        \n",
    "        last = [-1] * 26        \n",
    "        n = len(S)\n",
    "        nextpos = [-1] * n\n",
    "        for i in range(n)[::-1]:\n",
    "            key = ord(S[i]) - 97\n",
    "            nextpos[i] = last[key]\n",
    "            last[key] = i\n",
    "        \n",
    "        cur = 0\n",
    "        res = []\n",
    "        while cur < n:            \n",
    "            if nextpos[cur] != -1:\n",
    "                right = nextpos[cur]\n",
    "                k = cur\n",
    "                while k <= right:\n",
    "                    right = max(right, nextpos[k])\n",
    "                    k += 1\n",
    "                res.append(right - cur + 1)\n",
    "                cur = right + 1\n",
    "            else:\n",
    "                res.append(1)\n",
    "                cur += 1\n",
    "        return res"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "from typing import List\n",
    "import collections\n",
    "\n",
    "class Solution:\n",
    "    def partitionLabels(self, S: str) -> List[int]:\n",
    "        #首先找到每个元素出现的最后位置,字典的形式，通过元素找到下标\n",
    "        last={c:i for i,c in enumerate(S)}\n",
    "        #设置区间\n",
    "        start=end=0\n",
    "        #保存字符串的长度\n",
    "        res=[]\n",
    "        #开始遍历元素\"ababcbacadefegdehijhklij\"\n",
    "        for i,c in enumerate(S):\n",
    "            #设置尾部\n",
    "            end=max(end,last[c])\n",
    "            #当区间里所有元素都遍历过\n",
    "            if i==end:          \n",
    "                res.append(end-start+1)\n",
    "                start=i+1\n",
    "        return res\n",
    "\n",
    "\n",
    "        "
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "from typing import List\n",
    "import collections\n",
    "\n",
    "class Solution:\n",
    "    def partitionLabels(self, S: str) -> List[int]:\n",
    "        last_index = {c:i for i,c in enumerate(S)}\n",
    "        #统计每一个字母所在的最后位置\n",
    "        #根据index进行分割\n",
    "        j = split = 0\n",
    "        res = []\n",
    "        for i,c in enumerate(S):\n",
    "            j = max(j, last_index[c])\n",
    "            if i == j:\n",
    "                res.append(i - split + 1)\n",
    "                split = i+1\n",
    "            \n",
    "        return res\n",
    "\n"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "from typing import List\n",
    "import collections\n",
    "\n",
    "class Solution:\n",
    "    def partitionLabels(self, S: str) -> List[int]:\n",
    "        last = [0] * 26\n",
    "        for i, ch in enumerate(S):\n",
    "            last[ord(ch) - ord(\"a\")] = i\n",
    "        \n",
    "        partition = list()\n",
    "        start = end = 0\n",
    "        for i, ch in enumerate(S):\n",
    "            end = max(end, last[ord(ch) - ord(\"a\")])\n",
    "            if i == end:\n",
    "                partition.append(end - start + 1)\n",
    "                start = end + 1\n",
    "        \n",
    "        return partition\n"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "from typing import List\n",
    "import collections\n",
    "\n",
    "class Solution:\n",
    "    def partitionLabels(self, S: str) -> List[int]:\n",
    "        sl = list()\n",
    "        start = 0\n",
    "        for i in range(len(S)):\n",
    "            if set(S[start:i+1]) & set(S[i+1:]):\n",
    "                continue\n",
    "            else:\n",
    "                sl.append(i + 1-start)\n",
    "                start = i + 1\n",
    "        return sl"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "from typing import List\n",
    "import collections\n",
    "\n",
    "class Solution:\n",
    "    def partitionLabels(self, S: str):\n",
    "        dic = {s:index for index, s in enumerate(S)}\n",
    "        num = 0\n",
    "        result = []\n",
    "        j = dic[S[0]]\n",
    "        for i in range(len(S)):\n",
    "            num +=1\n",
    "            if dic[S[i]] > j: \n",
    "                j = dic[S[i]]\n",
    "            if i == j:\n",
    "                result.append(num)\n",
    "                num = 0\n",
    "        return result"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "from typing import List\n",
    "import collections\n",
    "\n",
    "class Solution:\n",
    "    def partitionLabels(self, S: str) -> List[int]:\n",
    "        n = len(S)\n",
    "        ans = []\n",
    "        def traverse(start):\n",
    "            if start > n - 1: return\n",
    "            stack = []\n",
    "            pending = []\n",
    "            for i in range(start, n):\n",
    "                if not stack:\n",
    "                    stack.append(S[i])\n",
    "                    start = i\n",
    "                else:\n",
    "                    if S[i] in stack:\n",
    "                        stack = stack + pending + [S[i]]\n",
    "                        start = i\n",
    "                        pending = []\n",
    "                    else:\n",
    "                        pending.append(S[i])\n",
    "            if stack:\n",
    "                ans.append(len(stack))\n",
    "            traverse(start + 1)\n",
    "        traverse(0)\n",
    "        return ans"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "from typing import List\n",
    "import collections\n",
    "\n",
    "class Solution:\n",
    "    def partitionLabels(self, S: str) -> List[int]:\n",
    "        res = []\n",
    "        char_dict = defaultdict(list)\n",
    "\n",
    "        for index, item in enumerate(S):\n",
    "            char_dict[item].append(index)\n",
    "        def pre(value: str, start):\n",
    "            if not value or start >= len(value):\n",
    "                return\n",
    "            right = 0\n",
    "            right_new = char_dict[value[start]][-1]\n",
    "            temp_start = start\n",
    "            while right_new > right:\n",
    "\n",
    "                right = right_new\n",
    "                char_set = set(value[temp_start:right_new + 1])\n",
    "                temp_start = right_new+1\n",
    "                for c in char_set:\n",
    "                    right_new = max(right_new, char_dict[c][-1])\n",
    "            res.append(right_new+1-start)\n",
    "            pre(S, right_new+1)\n",
    "        pre(S, 0)\n",
    "        return res"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "from typing import List\n",
    "import collections\n",
    "\n",
    "class Solution:\n",
    "    def partitionLabels(self, S: str) -> List[int]:\n",
    "        dic = {}\n",
    "        def calc_len(s):\n",
    "            if s in dic:\n",
    "                return dic[s]\n",
    "            n = len(s)\n",
    "            if n == 1:\n",
    "                return [1]\n",
    "            dp = [False] * n\n",
    "            dp[-1] = True\n",
    "            for i in range(n):\n",
    "                s1 = set(s[:i+1])\n",
    "                s2 = set(s[i+1:])\n",
    "                for w in s1:\n",
    "                    if w in s2:\n",
    "                        dp[i] = True\n",
    "                        break\n",
    "            if all(dp):\n",
    "                dic[s] = [n]\n",
    "                return [n]\n",
    "            ans = 1\n",
    "            res = [n]\n",
    "            for i in range(n):\n",
    "                if not dp[i]:\n",
    "                    left = calc_len(s[:i+1])\n",
    "                    right = calc_len(s[i+1:])\n",
    "                    if len(left) + len(right) > ans:\n",
    "                        ans = len(left) + len(right)\n",
    "                        res = left + right\n",
    "            dic[s] = res\n",
    "            return res\n",
    "        res = calc_len(S)\n",
    "        return res\n",
    "\n",
    "            \n",
    "\n",
    "            \n",
    "            \n"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "from typing import List\n",
    "import collections\n",
    "\n",
    "class Solution:\n",
    "    def partitionLabels(self, S: str) -> List[int]:\n",
    "        \n",
    "        #思路：贪心法   在处理数组前，统计一遍信息（如频率、个数、第一次出现位置、最后一次出现位置等）\n",
    "        # res = []\n",
    "        # dic = {}\n",
    "        # for index,ch in enumerate(S):  # 返回当前字母和索引\n",
    "        #     dic[ch] = index     #记录该字母最后一次出现的索引值\n",
    "        # #dic = {'a': 8, 'b': 5, 'c': 7, 'd': 14, 'e': 15, 'f': 11, 'g': 13, 'h': 19, 'i': 22, 'j': 23, 'k': 20, 'l': 21}\n",
    "        \n",
    "        # cur = dic[S[0]]     #返回字符串S第一个出现的字母，最后出现的索引值，\n",
    "\n",
    "        # for index,ch in enumerate(S):   #遍历一遍字符串S 返回信息（0，a）（1，b）(2,a).....\n",
    "        #     if dic[ch] > cur:       \n",
    "        #         cur = dic[ch]\n",
    "        #     if index == cur:\n",
    "        #         res.append(cur - sum(res) + 1)\n",
    "        # return res \n",
    "\n",
    "        res = []\n",
    "        dic = {}\n",
    "        for i,c in enumerate(S):\n",
    "            dic[c] = i \n",
    "        start = dic[S[0]]\n",
    "        for i,c in enumerate(S):\n",
    "            if dic[c] > start:\n",
    "                start = dic[c]\n",
    "            if i == start:\n",
    "                res.append(start - sum(res) + 1)\n",
    "        return res \n",
    "\n",
    "\n",
    "\n",
    "\n",
    "\n",
    "\n",
    "\n",
    "\n",
    "\n",
    "        # last = [0] * 26\n",
    "        # for i,ch in enumerate(S):\n",
    "        #     last[ord(ch) - ord('a')] = i\n",
    "        # partition = list()\n",
    "        # start = end = 0\n",
    "        # for i,ch in enumerate(S):\n",
    "        #     end = max(end,last[ord(ch) - ord('a')])\n",
    "        #     if i == end:\n",
    "        #         partition.append(end - start + 1)\n",
    "        #         start = end + 1\n",
    "        # return partition\n",
    "    \n",
    "\n"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "from typing import List\n",
    "import collections\n",
    "\n",
    "class Solution:\n",
    "    def partitionLabels(self, s: str) -> List[int]:\n",
    "        last = {c:i for i, c in enumerate(s)}\n",
    "        end = start = 0\n",
    "        res =[]\n",
    "        for i, c in enumerate(s):\n",
    "            end = max(end, last[c])\n",
    "            if i == end:\n",
    "                res.append(end - start + 1)\n",
    "                start = i + 1\n",
    "        return res"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "from typing import List\n",
    "import collections\n",
    "\n",
    "class Solution:\n",
    "    def partitionLabels(self, s: str) -> List[int]:\n",
    "        a = {}\n",
    "        for i in range(len(s)):\n",
    "            if s[i] not in a:\n",
    "                a[s[i]] = [i,i]\n",
    "            else:\n",
    "                a[s[i]][-1] = i\n",
    "        b = []\n",
    "        for i in a:\n",
    "            b.append(a[i])\n",
    "        \n",
    "        m = 0\n",
    "        n = b[0][1]\n",
    "        res = []\n",
    "        for i in b:\n",
    "            if i[0] <= n and i[1] <= n:\n",
    "                continue\n",
    "            elif i[0] <= n and i[1] > n:\n",
    "                n = i[1]\n",
    "            elif i[0] > n:\n",
    "                res.append(n - m + 1)\n",
    "                m = i[0]\n",
    "                n = i[1]\n",
    "        res.append(n - m + 1)\n",
    "        return res\n",
    "        \n",
    "            \n"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "from typing import List\n",
    "import collections\n",
    "\n",
    "class Solution:\n",
    "    def partitionLabels(self, s: str) -> List[int]:\n",
    "        hash_table = [0] * 26\n",
    "        for i in range(len(s)):\n",
    "            hash_table[ord(s[i]) - ord('a')] = i\n",
    "        \n",
    "        results = []\n",
    "        left = 0\n",
    "        right = 0\n",
    "        for i in range(len(s)):\n",
    "            right = max(right, hash_table[ord(s[i]) - ord('a')])\n",
    "            if right == i:\n",
    "                results.append(right - left + 1)\n",
    "                left, right = i+1, i+1\n",
    "        return results"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "from typing import List\n",
    "import collections\n",
    "\n",
    "class Solution:\n",
    "    def partitionLabels(self, s: str) -> List[int]:\n",
    "        res = dict()\n",
    "        f = []\n",
    "        for i in range(len(s)):\n",
    "            res[s[i]] = i\n",
    "        for i in range(len(s)):\n",
    "            f.append(res[s[i]])\n",
    "        index = 0\n",
    "        res = []\n",
    "        print(f)\n",
    "        while index < len(s):\n",
    "            end = f[index]\n",
    "            if end == index:\n",
    "                res.append(1)\n",
    "                index += 1\n",
    "                continue\n",
    "            while max(f[index: end]) != f[end]:\n",
    "                end = max(f[index: end])\n",
    "            res.append(end - index + 1)\n",
    "            index = end + 1\n",
    "        return res\n",
    "                \n",
    "                \n",
    "            "
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "from typing import List\n",
    "import collections\n",
    "\n",
    "class Solution:\n",
    "    def partitionLabels(self, s: str) -> List[int]:\n",
    "        # 贪心策略\n",
    "        # 目标是找到最多的不相交子集\n",
    "        # 即 子集1 ∩ 子集2 = ∅\n",
    "        # 所以，当有子母同时出现在多个集合中，可以将其合并\n",
    "\n",
    "        # 预处理\n",
    "        # 提取每个字母开头结尾的索引构成列表\n",
    "        front_end_list =  []\n",
    "        pointer = []\n",
    "        for idx, word in enumerate(s):\n",
    "            all_ = [i for i,x in enumerate(s) if x==word]\n",
    "            if not (idx in pointer):\n",
    "                front_end_list.append([all_[0],all_[-1]])\n",
    "            for j in all_:\n",
    "                pointer.append(j)\n",
    "        \n",
    "        ans = []\n",
    "        set_ = front_end_list[0]\n",
    "        if len(front_end_list) == 1:\n",
    "            ans.append(set_[1] - set_[0] + 1)\n",
    "            return ans\n",
    "\n",
    "        # 从左至右遍历集合\n",
    "        # 如果集合相交则合并，直到找到下一个不相交的集合\n",
    "        for idx in range(1, len(front_end_list)):\n",
    "            # 判断两个集合相交：集合2的开始 <= 集合1的结尾\n",
    "            if front_end_list[idx][0] <= set_[1]:\n",
    "                set_[1] = max(front_end_list[idx][1], set_[1])\n",
    "            # 判断两个集合不相交：集合2的开始 > 集合1的结尾\n",
    "            else:\n",
    "                ans.append(set_[1] - set_[0] + 1)\n",
    "                set_ = front_end_list[idx]\n",
    "            if idx == len(front_end_list) - 1:\n",
    "                ans.append(set_[1] - set_[0] + 1)\n",
    "\n",
    "        return ans"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "from typing import List\n",
    "import collections\n",
    "\n",
    "class Solution:\n",
    "    def partitionLabels(self, s: str) -> List[int]:\n",
    "        hash = {}\n",
    "        for i in s:\n",
    "            if i not in hash:\n",
    "                hash[i] = s.rfind(i)\n",
    "        result = []\n",
    "        tmp = hash[s[0]]\n",
    "        tmp_str = s[0]\n",
    "        length = 0\n",
    "        for i in range(len(s) - 1):\n",
    "            if i == tmp:\n",
    "                result.append(length + 1)\n",
    "                length = 0\n",
    "                tmp = hash[s[i + 1]]\n",
    "                tmp_str = s[i + 1]\n",
    "            else:\n",
    "                length += 1\n",
    "                if hash[s[i]] > tmp:\n",
    "                    tmp = hash[s[i]]\n",
    "                    tmp_str = s[i]\n",
    "        result.append(length + 1)\n",
    "        return result\n"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "from typing import List\n",
    "import collections\n",
    "\n",
    "class Solution:\n",
    "    def partitionLabels(self, s: str) -> List[int]:\n",
    "        tail_idx=0\n",
    "        res = []\n",
    "        for i in range(len(s)):\n",
    "            # 在后面寻找a[i]\n",
    "            if s[i] in s[i+1:]:\n",
    "                tail_idx  = max(s[i+1:].index(s[i])+i +1 , tail_idx)\n",
    "            if i>=tail_idx:\n",
    "                res.append(i)\n",
    "        x = -1\n",
    "        t = []\n",
    "        for num in res:\n",
    "            t.append(num-x)\n",
    "            x = num\n",
    "        if not t:\n",
    "            t.append(len(s))\n",
    "        return t\n"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "from typing import List\n",
    "import collections\n",
    "\n",
    "class Solution:\n",
    "    def partitionLabels(self, s: str) -> List[int]:\n",
    "\n",
    "        letter_interval = dict()\n",
    "\n",
    "        for index, letter in enumerate(s):\n",
    "            if letter not in letter_interval:\n",
    "                letter_interval[letter] = [index, index]\n",
    "            else:\n",
    "                current_interval = letter_interval[letter]\n",
    "                if len(current_interval)<2:\n",
    "                    letter_interval[letter].append(index)\n",
    "                else:\n",
    "                    letter_interval[letter][1] = index\n",
    "\n",
    "        interval_list = [interval for interval in letter_interval.values()]\n",
    "\n",
    "        n_unique_letters = len(interval_list)\n",
    "\n",
    "        final_res = []\n",
    "        current_interval_len = interval_list[0][1] + 1 \n",
    "        prev_end = interval_list[0][1]\n",
    "        for cur_index in range(1, n_unique_letters):\n",
    "\n",
    "            cur_start = interval_list[cur_index][0]\n",
    "            cur_end = interval_list[cur_index][1]\n",
    "            \n",
    "            if cur_start < prev_end:\n",
    "                if cur_end > prev_end:\n",
    "                    current_interval_len += cur_end - prev_end\n",
    "                    prev_end = cur_end\n",
    "            else:\n",
    "                final_res.append(current_interval_len)\n",
    "                prev_end = cur_end\n",
    "                current_interval_len = cur_end - cur_start + 1\n",
    "        final_res.append(current_interval_len)\n",
    "        return final_res\n",
    "\n"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "from typing import List\n",
    "import collections\n",
    "\n",
    "# Definition for singly-linked list.\n",
    "# class ListNode:\n",
    "#     def __init__(self, x):\n",
    "#         self.val = x\n",
    "#         self.next = None\n",
    "\n",
    "class Solution:\n",
    "    def partition(self, head: ListNode, x: int) -> ListNode:\n",
    "        cnt = head\n",
    "        st,end=ListNode(0),ListNode(0)\n",
    "        s1=st\n",
    "        e1 = end\n",
    "        while head:\n",
    "            if head.val<x:\n",
    "                s1.next = head\n",
    "                s1 = s1.next\n",
    "            else:\n",
    "                e1.next = head\n",
    "                e1 = e1.next\n",
    "            head = head.next\n",
    "        s1.next = end.next\n",
    "        e1.next = None\n",
    "        return st.next\n",
    "\n",
    "\n"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "from typing import List\n",
    "import collections\n",
    "\n",
    "# Definition for singly-linked list.\n",
    "# class ListNode:\n",
    "#     def __init__(self, x):\n",
    "#         self.val = x\n",
    "#         self.next = None\n",
    "\n",
    "class Solution:\n",
    "    def partition(self, head: ListNode, x: int) -> ListNode:\n",
    "        if head is None:\n",
    "            return None\n",
    "        small = ListNode(-1)\n",
    "        big = ListNode(-1)\n",
    "        l1 = small\n",
    "        l2 = big\n",
    "        cur = head\n",
    "        while cur:\n",
    "            if cur.val >= x:\n",
    "                l2.next = cur\n",
    "                l2 = l2.next\n",
    "            else:\n",
    "                l1.next = cur\n",
    "                l1 = l1.next\n",
    "            cur = cur.next\n",
    "        l2.next = None\n",
    "        l1.next = big.next\n",
    "        return small.next"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "from typing import List\n",
    "import collections\n",
    "\n",
    "# Definition for singly-linked list.\n",
    "# class ListNode:\n",
    "#     def __init__(self, x):\n",
    "#         self.val = x\n",
    "#         self.next = None\n",
    "\n",
    "class Solution:\n",
    "    def partition(self, head: ListNode, x: int) -> ListNode:\n",
    "        if not head or not head.next:\n",
    "            return head\n",
    "\n",
    "        cur = head\n",
    "        l1, l2 = ListNode(-101), ListNode(-101)\n",
    "        l1cur, l2cur = l1, l2\n",
    "        while cur:\n",
    "            if cur.val < x:\n",
    "                l1cur.next = cur\n",
    "                l1cur = l1cur.next\n",
    "            else:\n",
    "                l2cur.next = cur\n",
    "                l2cur = l2cur.next\n",
    "            cur = cur.next\n",
    "\n",
    "        l2cur.next = None\n",
    "        l1cur.next = l2.next\n",
    "        return l1.next\n"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "from typing import List\n",
    "import collections\n",
    "\n",
    "# Definition for singly-linked list.\n",
    "# class ListNode:\n",
    "#     def __init__(self, x):\n",
    "#         self.val = x\n",
    "#         self.next = None\n",
    "\n",
    "class Solution:\n",
    "    def partition(self, head: ListNode, x: int) -> ListNode:\n",
    "        sml_dummy, big_dummy = ListNode(0), ListNode(0)\n",
    "        sml, big = sml_dummy, big_dummy\n",
    "        while head:\n",
    "            if head.val < x:\n",
    "                sml.next = head\n",
    "                sml = sml.next\n",
    "            else:\n",
    "                big.next = head\n",
    "                big = big.next\n",
    "            head = head.next\n",
    "        sml.next = big_dummy.next\n",
    "        big.next = None\n",
    "        return sml_dummy.next"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "from typing import List\n",
    "import collections\n",
    "\n",
    "# Definition for singly-linked list.\n",
    "# class ListNode:\n",
    "#     def __init__(self, x):\n",
    "#         self.val = x\n",
    "#         self.next = None\n",
    "\n",
    "class Solution:\n",
    "    def partition(self, head: ListNode, x: int) -> ListNode:\n",
    "        min_list_head = None\n",
    "        min_list_tail = None\n",
    "        max_list_head = None\n",
    "        max_list_tail = None\n",
    "        while head:\n",
    "            temp = head\n",
    "            if head.val<x:\n",
    "                if min_list_head:\n",
    "                    min_list_tail.next = temp\n",
    "                    min_list_tail = min_list_tail.next\n",
    "                else:\n",
    "                    min_list_head = temp\n",
    "                    min_list_tail = temp\n",
    "            else:\n",
    "                if max_list_head:\n",
    "                    max_list_tail.next = temp\n",
    "                    max_list_tail = max_list_tail.next\n",
    "                else:\n",
    "                    max_list_head = temp\n",
    "                    max_list_tail = temp\n",
    "            head = head.next\n",
    "            temp.next = None\n",
    "        if min_list_head:\n",
    "            min_list_tail.next = max_list_head\n",
    "            return min_list_head\n",
    "        if max_list_head:\n",
    "            return max_list_head"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "from typing import List\n",
    "import collections\n",
    "\n",
    "# Definition for singly-linked list.\n",
    "# class ListNode:\n",
    "#     def __init__(self, x):\n",
    "#         self.val = x\n",
    "#         self.next = None\n",
    "\n",
    "class Solution:\n",
    "    def partition(self, head: ListNode, x: int) -> ListNode:\n",
    "        if not head:    return None\n",
    "        if not head.next:   return head\n",
    "        p = head\n",
    "        q = head.next\n",
    "        while q!= None:\n",
    "            flag = 0\n",
    "            while p!= None and p.val < x:\n",
    "                if p == q:\n",
    "                    flag = 1\n",
    "                p = p.next\n",
    "            if p == None:   return head\n",
    "\n",
    "            while q!= None and q.val >= x:\n",
    "                q = q.next\n",
    "            if flag == 1:\n",
    "                while q != p:\n",
    "                    q = q.next\n",
    "            if q == None:   return head\n",
    "            \n",
    "            p.val, q.val = q.val, p.val\n"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "from typing import List\n",
    "import collections\n",
    "\n",
    "# Definition for singly-linked list.\n",
    "# class ListNode:\n",
    "#     def __init__(self, x):\n",
    "#         self.val = x\n",
    "#         self.next = None\n",
    "\n",
    "class Solution:\n",
    "    def partition(self, head: ListNode, x: int) -> ListNode:\n",
    "        sml_dummy,big_dummy=ListNode(0),ListNode(0)\n",
    "        sml,big=sml_dummy,big_dummy\n",
    "        while head:\n",
    "            if head.val<x:\n",
    "                sml.next=head\n",
    "                sml=sml.next\n",
    "            else:\n",
    "                big.next=head\n",
    "                big=big.next\n",
    "            head=head.next\n",
    "        sml.next=big_dummy.next\n",
    "        big.next=None\n",
    "        return sml_dummy.next"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "from typing import List\n",
    "import collections\n",
    "\n",
    "# Definition for singly-linked list.\n",
    "# class ListNode:\n",
    "#     def __init__(self, x):\n",
    "#         self.val = x\n",
    "#         self.next = None\n",
    "\n",
    "class Solution:\n",
    "    def partition(self, head: ListNode, x: int) -> ListNode:\n",
    "        cur=pre=head\n",
    "        while pre:\n",
    "            if pre.val<x:\n",
    "                pre.val,cur.val=cur.val,pre.val\n",
    "                cur=cur.next\n",
    "            pre=pre.next\n",
    "        return head"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "from typing import List\n",
    "import collections\n",
    "\n",
    "# Definition for singly-linked list.\n",
    "# class ListNode:\n",
    "#     def __init__(self, x):\n",
    "#         self.val = x\n",
    "#         self.next = None\n",
    "\n",
    "class Solution:\n",
    "    def partition(self, head: ListNode, x: int) -> ListNode:\n",
    "        sml_dummy, big_dummy = ListNode(0), ListNode(0)\n",
    "        sml, big = sml_dummy, big_dummy\n",
    "        while head:\n",
    "            if head.val < x:\n",
    "                sml.next = head\n",
    "                sml = sml.next\n",
    "            else:\n",
    "                big.next = head\n",
    "                big = big.next\n",
    "            head = head.next\n",
    "        sml.next = big_dummy.next\n",
    "        big.next = None\n",
    "        return sml_dummy.next\n"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "from typing import List\n",
    "import collections\n",
    "\n",
    "# Definition for singly-linked list.\n",
    "# class ListNode:\n",
    "#     def __init__(self, x):\n",
    "#         self.val = x\n",
    "#         self.next = None\n",
    "\n",
    "class Solution:\n",
    "    def partition(self, head: ListNode, x: int) -> ListNode:\n",
    "        dummy1 = ListNode()\n",
    "        dummy2 = ListNode()\n",
    "        smaller = dummy1\n",
    "        greater = dummy2\n",
    "        current = head\n",
    "        \n",
    "        while current:\n",
    "            if current.val < x:\n",
    "                smaller.next = current\n",
    "                smaller = smaller.next\n",
    "            else:\n",
    "                greater.next = current\n",
    "                greater = greater.next\n",
    "            current = current.next\n",
    "        smaller.next = dummy2.next\n",
    "        greater.next = None\n",
    "        return dummy1.next\n",
    "\n"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "from typing import List\n",
    "import collections\n",
    "\n",
    "# Definition for singly-linked list.\n",
    "# class ListNode:\n",
    "#     def __init__(self, x):\n",
    "#         self.val = x\n",
    "#         self.next = None\n",
    "\n",
    "class Solution:\n",
    "    def partition(self, head: ListNode, x: int) -> ListNode:\n",
    "        small_q = ListNode(-1)\n",
    "        bigger_q = ListNode(-1)\n",
    "\n",
    "        cur_s = small_q\n",
    "        cur_b = bigger_q\n",
    "\n",
    "        cur_h = head\n",
    "\n",
    "        while cur_h:\n",
    "            if cur_h.val < x:\n",
    "                cur_s.next = cur_h\n",
    "                cur_s = cur_s.next\n",
    "            else:\n",
    "                cur_b.next = cur_h\n",
    "                cur_b = cur_b.next\n",
    "            cur_h = cur_h.next\n",
    "\n",
    "        cur_s.next = bigger_q.next\n",
    "        cur_b.next = None  # Ensure the end of the \"bigger\" list is None\n",
    "\n",
    "        return small_q.next\n"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "from typing import List\n",
    "import collections\n",
    "\n",
    "# Definition for singly-linked list.\n",
    "# class ListNode:\n",
    "#     def __init__(self, x):\n",
    "#         self.val = x\n",
    "#         self.next = None\n",
    "\n",
    "class Solution:\n",
    "    def partition(self, head: ListNode, x: int) -> ListNode:\n",
    "        res_small = smaller = ListNode()\n",
    "        res_large = larger = ListNode()\n",
    "        while head:\n",
    "            if head.val >= x:\n",
    "                larger.next = ListNode(head.val)\n",
    "                larger = larger.next\n",
    "            else:\n",
    "                smaller.next = ListNode(head.val)\n",
    "                smaller = smaller.next\n",
    "            head = head.next\n",
    "        smaller.next = res_large.next\n",
    "        return res_small.next"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "from typing import List\n",
    "import collections\n",
    "\n",
    "# Definition for singly-linked list.\n",
    "# class ListNode:\n",
    "#     def __init__(self, x):\n",
    "#         self.val = x\n",
    "#         self.next = None\n",
    "\n",
    "class Solution:\n",
    "    def partition(self, head: ListNode, x: int) -> ListNode:\n",
    "        if not head or not head.next:\n",
    "            return head\n",
    "\n",
    "        cur = head\n",
    "        l1, l2 = ListNode(-101), ListNode(-101)\n",
    "        l1cur, l2cur = l1, l2\n",
    "        while cur:\n",
    "            if cur.val < x:\n",
    "                l1cur.next = cur\n",
    "                l1cur = l1cur.next\n",
    "            else:\n",
    "                l2cur.next = cur\n",
    "                l2cur = l2cur.next\n",
    "            cur = cur.next\n",
    "\n",
    "        l2cur.next = None\n",
    "        l1cur.next = l2.next\n",
    "        return l1.next"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "from typing import List\n",
    "import collections\n",
    "\n",
    "# Definition for singly-linked list.\n",
    "# class ListNode:\n",
    "#     def __init__(self, x):\n",
    "#         self.val = x\n",
    "#         self.next = None\n",
    "\n",
    "class Solution:\n",
    "    def partition(self, head: Optional[ListNode], x: int) -> Optional[ListNode]:\n",
    "        small = ListNode()\n",
    "        large = ListNode()\n",
    "        \n",
    "        pre_small = small\n",
    "        pre_large = large\n",
    "        \n",
    "        while head:\n",
    "            if head.val < x:\n",
    "                small.next = head\n",
    "                small = small.next\n",
    "            else:\n",
    "                large.next = head\n",
    "                large = large.next\n",
    "            \n",
    "            head = head.next\n",
    "        \n",
    "        large.next = None\n",
    "        small.next = pre_large.next\n",
    "        return pre_small.next\n",
    "\n",
    "        "
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "from typing import List\n",
    "import collections\n",
    "\n",
    "# Definition for singly-linked list.\n",
    "# class ListNode:\n",
    "#     def __init__(self, x):\n",
    "#         self.val = x\n",
    "#         self.next = None\n",
    "\n",
    "class Solution:\n",
    "    def partition(self, head: ListNode, x: int) -> ListNode:\n",
    "        # less, l cur\n",
    "        le = lc = ListNode(0)\n",
    "        # great_equal, g cur\n",
    "        ge = gc = ListNode(0)\n",
    "        while head:\n",
    "            if head.val < x:\n",
    "                lc.next = head  # ListNode(head.val)\n",
    "                lc = lc.next\n",
    "            else:\n",
    "                gc.next = head  # ListNode(head.val)\n",
    "                gc = gc.next\n",
    "            head = head.next\n",
    "        lc.next = ge.next\n",
    "        gc.next = None  # !\n",
    "        return le.next\n",
    "        "
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "from typing import List\n",
    "import collections\n",
    "\n",
    "# Definition for singly-linked list.\n",
    "# class ListNode:\n",
    "#     def __init__(self, x):\n",
    "#         self.val = x\n",
    "#         self.next = None\n",
    "\n",
    "class Solution:\n",
    "    def partition(self, head: ListNode, x: int) -> ListNode:\n",
    "        op1, op2 = ListNode(0), ListNode(0)\n",
    "        p1 = op1\n",
    "        p2 = op2\n",
    "        op = head\n",
    "        while op:\n",
    "            if op.val >= x:\n",
    "                op2.next = op\n",
    "                op2 = op\n",
    "            else:\n",
    "                op1.next = op\n",
    "                op1 = op\n",
    "            op = op.next\n",
    "        op2.next = None\n",
    "        op1.next = p2.next\n",
    "        return p1.next\n",
    "            "
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "from typing import List\n",
    "import collections\n",
    "\n",
    "# Definition for singly-linked list.\n",
    "# class ListNode:\n",
    "#     def __init__(self, x):\n",
    "#         self.val = x\n",
    "#         self.next = None\n",
    "\n",
    "class Solution:\n",
    "    def partition(self, head: ListNode, x: int) -> ListNode:\n",
    "        \n",
    "        lt = ListNode()\n",
    "        gt = ListNode()\n",
    "        tmp_lt, tmp_gt = lt, gt\n",
    "        tmp = head\n",
    "        while tmp:\n",
    "            tmp_next = tmp.next\n",
    "            if tmp.val < x:\n",
    "                tmp_lt.next = tmp\n",
    "                tmp.next = None\n",
    "                tmp_lt = tmp_lt.next\n",
    "            else:\n",
    "                tmp_gt.next = tmp\n",
    "                tmp.next = None\n",
    "                tmp_gt = tmp_gt.next\n",
    "            tmp = tmp_next\n",
    "        tmp_lt.next = gt.next\n",
    "        return lt.next"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "from typing import List\n",
    "import collections\n",
    "\n",
    "# Definition for singly-linked list.\n",
    "# class ListNode:\n",
    "#     def __init__(self, x):\n",
    "#         self.val = x\n",
    "#         self.next = None\n",
    "\n",
    "class Solution:\n",
    "    def partition(self, head: ListNode, x: int) -> ListNode:\n",
    "        head1 = ListNode(0)\n",
    "        head2 = ListNode(0)\n",
    "        cur = head\n",
    "        cur1 = head1\n",
    "        cur2 = head2\n",
    "        while cur:\n",
    "            if cur.val < x:\n",
    "                cur1.next = cur\n",
    "                cur1 = cur1.next\n",
    "            else:\n",
    "                cur2.next = cur\n",
    "                cur2 = cur2.next\n",
    "            cur = cur.next\n",
    "        cur1.next = head2.next\n",
    "        cur2.next = None\n",
    "        return head1.next\n",
    "        \n",
    "        \n"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "from typing import List\n",
    "import collections\n",
    "\n",
    "# Definition for singly-linked list.\n",
    "# class ListNode:\n",
    "#     def __init__(self, x):\n",
    "#         self.val = x\n",
    "#         self.next = None\n",
    "\n",
    "class Solution:\n",
    "    def partition(self, head: ListNode, x: int) -> ListNode:\n",
    "        p = None\n",
    "        t = head\n",
    "        r = None\n",
    "        tail = None\n",
    "        flag = False\n",
    "        F = False\n",
    "        if t is None:\n",
    "            return\n",
    "        while t is not None:\n",
    "            if t.val < x and p is None:\n",
    "                r = t\n",
    "                tail = t\n",
    "                t = t.next\n",
    "                continue\n",
    "            if t.val >= x and p is None:\n",
    "                p = t\n",
    "                tail = p\n",
    "                F = False\n",
    "                if r is None:\n",
    "                    flag = True\n",
    "                t = t.next\n",
    "                continue\n",
    "            if t.val < x and p is not None:\n",
    "                if flag:\n",
    "                    r = t\n",
    "                    new = t.next\n",
    "                    t.next = p\n",
    "                    t=new\n",
    "                    flag = False\n",
    "                    head = r\n",
    "                    tail.next = t\n",
    "                    continue\n",
    "                else:\n",
    "                    new = t.next\n",
    "                    t.next=p\n",
    "                    r.next=t\n",
    "                    r = r.next\n",
    "                    t = new\n",
    "                    tail.next = t\n",
    "                continue\n",
    "            if t.val >= x and p is not None:\n",
    "                if not F:\n",
    "                    p.next = t\n",
    "                    tail = t\n",
    "                    F = True\n",
    "                elif F:\n",
    "                    tail.next = t\n",
    "                    tail = t\n",
    "                t = t.next\n",
    "        return head\n"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "from typing import List\n",
    "import collections\n",
    "\n",
    "# Definition for singly-linked list.\n",
    "# class ListNode:\n",
    "#     def __init__(self, x):\n",
    "#         self.val = x\n",
    "#         self.next = None\n",
    "\n",
    "class Solution:\n",
    "    def partition(self, head: ListNode, x: int) -> ListNode:\n",
    "\n",
    "        # 头插法\n",
    "\n",
    "        if not head:\n",
    "            return head\n",
    "\n",
    "        prehead = ListNode(-1, head)\n",
    "\n",
    "        pre = prehead\n",
    "        cur = head\n",
    "\n",
    "        if head.val < x:\n",
    "            pre = pre.next\n",
    "            cur = cur.next\n",
    "\n",
    "        while cur:\n",
    "            if cur.val < x:\n",
    "                pre.next = cur.next\n",
    "                cur.next = prehead.next\n",
    "                prehead.next = cur\n",
    "                cur = pre.next\n",
    "            else:\n",
    "                pre = pre.next\n",
    "                cur = cur.next\n",
    "\n",
    "        return prehead.next\n",
    "\n",
    "\n",
    "        # 拼接法\n",
    "        \n",
    "        # small = ListNode(None)\n",
    "\n",
    "        # large = ListNode(None)\n",
    "\n",
    "        # sml = small\n",
    "        # lag = large\n",
    "\n",
    "        # while head:\n",
    "        #     if head.val < x:\n",
    "        #         sml.next = head\n",
    "        #         sml = sml.next\n",
    "        #     else:\n",
    "        #         lag.next = head\n",
    "        #         lag = lag.next\n",
    "        #     head = head.next\n",
    "\n",
    "        # sml.next = large.next\n",
    "        # lag.next = None\n",
    "\n",
    "        # return small.next\n",
    "\n"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "from typing import List\n",
    "import collections\n",
    "\n",
    "# Definition for singly-linked list.\n",
    "# class ListNode:\n",
    "#     def __init__(self, x):\n",
    "#         self.val = x\n",
    "#         self.next = None\n",
    "\n",
    "class Solution:\n",
    "    def partition(self, head: ListNode, x: int) -> ListNode:\n",
    "        small = ListNode(0)\n",
    "        large = ListNode(0)\n",
    "\n",
    "        small_dummy = small\n",
    "        large_dummy = large\n",
    "\n",
    "        while head:\n",
    "            if head.val < x:\n",
    "                small.next = head\n",
    "                small = small.next\n",
    "            else:\n",
    "                large.next = head\n",
    "                large = large.next\n",
    "            head = head.next\n",
    "        \n",
    "        small.next = large_dummy.next\n",
    "        large.next = None\n",
    "\n",
    "        return small_dummy.next"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "from typing import List\n",
    "import collections\n",
    "\n",
    "# Definition for singly-linked list.\n",
    "# class ListNode:\n",
    "#     def __init__(self, x):\n",
    "#         self.val = x\n",
    "#         self.next = None\n",
    "\n",
    "class Solution:\n",
    "    def partition(self, head: ListNode, x: int) -> ListNode:\n",
    "        new_head, pre_head = ListNode(x), ListNode(x)\n",
    "        s, t = new_head, pre_head\n",
    "        while head:\n",
    "            if head.val < x:\n",
    "                s.next = head\n",
    "                s = s.next\n",
    "            \n",
    "            else :\n",
    "                t.next = head\n",
    "                t = t.next\n",
    "            head = head.next\n",
    "        s.next = pre_head.next\n",
    "        t.next = None\n",
    "        return new_head.next\n",
    "\n",
    "\n",
    "            \n",
    "        "
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "from typing import List\n",
    "import collections\n",
    "\n",
    "# Definition for singly-linked list.\n",
    "# class ListNode:\n",
    "#     def __init__(self, x):\n",
    "#         self.val = x\n",
    "#         self.next = None\n",
    "\n",
    "class Solution:\n",
    "    def partition(self, head: ListNode, x: int) -> ListNode:\n",
    "        if head is None or head.next is None:\n",
    "            return head\n",
    "        pt = head\n",
    "        small = ListNode(-1)\n",
    "        big = ListNode(-2)\n",
    "        pt_small = small\n",
    "        pt_big = big\n",
    "        while pt:\n",
    "            if pt.val>=x:\n",
    "                pt_big.next = pt\n",
    "                pt_big = pt_big.next\n",
    "            else:\n",
    "                pt_small.next = pt\n",
    "                pt_small = pt_small.next\n",
    "                \n",
    "            pt = pt.next\n",
    "            pt_big.next = None\n",
    "            pt_small.next = None\n",
    "        pt_small.next = big.next\n",
    "        return small.next\n",
    "\n"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "from typing import List\n",
    "import collections\n",
    "\n",
    "# Definition for singly-linked list.\n",
    "# class ListNode:\n",
    "#     def __init__(self, x):\n",
    "#         self.val = x\n",
    "#         self.next = None\n",
    "\n",
    "class Solution:\n",
    "    def partition(self, head: ListNode, x: int) -> ListNode:\n",
    "        sml_dummy, big_dummy = ListNode(0), ListNode(0)\n",
    "        sml, big = sml_dummy, big_dummy\n",
    "        while head:\n",
    "            if head.val < x:\n",
    "                sml.next = head\n",
    "                sml = sml.next\n",
    "            else:\n",
    "                big.next = head\n",
    "                big = big.next\n",
    "            head = head.next\n",
    "        sml.next = big_dummy.next\n",
    "        big.next = None\n",
    "        return sml_dummy.next\n",
    "        "
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "from typing import List\n",
    "import collections\n",
    "\n",
    "class Solution:\n",
    "    def partition(self, head: ListNode, x: int) -> ListNode:\n",
    "        sml_dummy, big_dummy = ListNode(0), ListNode(0)\n",
    "        sml, big = sml_dummy, big_dummy\n",
    "        while head:\n",
    "            if head.val < x:\n",
    "                sml.next = head\n",
    "                sml = sml.next\n",
    "            else:\n",
    "                big.next = head\n",
    "                big = big.next\n",
    "            head = head.next\n",
    "        sml.next = big_dummy.next\n",
    "        big.next = None\n",
    "        return sml_dummy.next"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "from typing import List\n",
    "import collections\n",
    "\n",
    "# Definition for singly-linked list.\n",
    "# class ListNode:\n",
    "#     def __init__(self, x):\n",
    "#         self.val = x\n",
    "#         self.next = None\n",
    "\n",
    "class Solution:\n",
    "    def partition(self, head: ListNode, x: int) -> ListNode:\n",
    "        left, right = ListNode(0), ListNode(0)\n",
    "        temp1, temp2 = left, right\n",
    "        cur = head\n",
    "        while cur:\n",
    "            if cur.val < x:\n",
    "                left.next = cur\n",
    "                left = left.next\n",
    "            else:\n",
    "                right.next = cur\n",
    "                right = right.next\n",
    "            cur = cur.next\n",
    "        left.next = temp2.next\n",
    "        right.next = None\n",
    "        return temp1.next\n"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "from typing import List\n",
    "import collections\n",
    "\n",
    "# Definition for singly-linked list.\n",
    "# class ListNode:\n",
    "#     def __init__(self, x):\n",
    "#         self.val = x\n",
    "#         self.next = None\n",
    "\n",
    "class Solution:\n",
    "    def partition(self, head: ListNode, x: int) -> ListNode:\n",
    "        op1, op2 = ListNode(0), ListNode(0)\n",
    "        p1 = op1\n",
    "        p2 = op2\n",
    "        op = head\n",
    "        while op:\n",
    "            if op.val >= x:\n",
    "                op2.next = op\n",
    "                op2 = op\n",
    "            else:\n",
    "                op1.next = op\n",
    "                op1 = op\n",
    "            op = op.next\n",
    "        op2.next = None\n",
    "        op1.next = p2.next\n",
    "        return p1.next\n",
    "            "
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "from typing import List\n",
    "import collections\n",
    "\n",
    "# Definition for singly-linked list.\n",
    "# class ListNode:\n",
    "#     def __init__(self, x):\n",
    "#         self.val = x\n",
    "#         self.next = None\n",
    "\n",
    "class Solution:\n",
    "    def partition(self, head: ListNode, x: int) -> ListNode:\n",
    "        le = lc = ListNode(0)\n",
    "        ge = gc = ListNode(0)\n",
    "        while head:\n",
    "            if head.val < x:\n",
    "                lc.next = head  # ListNode(head.val)\n",
    "                lc = lc.next\n",
    "            else:\n",
    "                gc.next = head  # ListNode(head.val)\n",
    "                gc = gc.next\n",
    "            head = head.next\n",
    "        lc.next = ge.next\n",
    "        gc.next = None  # !\n",
    "        return le.next\n",
    "        "
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "from typing import List\n",
    "import collections\n",
    "\n",
    "# Definition for singly-linked list.\n",
    "# class ListNode:\n",
    "#     def __init__(self, x):\n",
    "#         self.val = x\n",
    "#         self.next = None\n",
    "\n",
    "class Solution:\n",
    "    def partition(self, head: ListNode, x: int) -> ListNode:\n",
    "            \n",
    "        l1 = ListNode(-1)\n",
    "        l2 = ListNode(-1)\n",
    "        less = l1\n",
    "        more = l2\n",
    "        while head:\n",
    "            if head.val < x:\n",
    "                l1.next = head\n",
    "                l1 = l1.next\n",
    "            else:\n",
    "                l2.next = head\n",
    "                l2 = l2.next\n",
    "            head = head.next\n",
    "        l1.next = more.next\n",
    "        l2.next = None\n",
    "        return less.next"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "from typing import List\n",
    "import collections\n",
    "\n",
    "# Definition for singly-linked list.\n",
    "# class ListNode:\n",
    "#     def __init__(self, x):\n",
    "#         self.val = x\n",
    "#         self.next = None\n",
    "\n",
    "class Solution:\n",
    "    def partition(self, head: ListNode, x: int) -> ListNode:\n",
    "        if not head:\n",
    "            return None\n",
    "        l1, l2 = ListNode(0), ListNode(0)\n",
    "        p1, p2 = l1, l2\n",
    "        while head:\n",
    "            if head.val < x:\n",
    "                p1.next = head\n",
    "                p1 = p1.next\n",
    "            else:\n",
    "                p2.next = head\n",
    "                p2 = p2.next\n",
    "            head = head.next\n",
    "        if p2.next:\n",
    "            p2.next = None\n",
    "            p1.next = l2.next\n",
    "        else:\n",
    "            p1.next = None\n",
    "            p1.next = l2.next\n",
    "        return l1.next"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "from typing import List\n",
    "import collections\n",
    "\n",
    "# Definition for singly-linked list.\n",
    "# class ListNode:\n",
    "#     def __init__(self, x):\n",
    "#         self.val = x\n",
    "#         self.next = None\n",
    "\n",
    "class Solution:\n",
    "    def partition(self, head: ListNode, x: int) -> ListNode:\n",
    "        first, second = head, head\n",
    "        while first:\n",
    "            if first.val < x:\n",
    "                first.val, second.val = second.val, first.val\n",
    "                first = first.next\n",
    "                second = second.next\n",
    "            else:\n",
    "                first = first.next\n",
    "        return head"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "from typing import List\n",
    "import collections\n",
    "\n",
    "# Definition for singly-linked list.\n",
    "# class ListNode:\n",
    "#     def __init__(self, x):\n",
    "#         self.val = x\n",
    "#         self.next = None\n",
    "\n",
    "class Solution:\n",
    "    def partition(self, head: ListNode, x: int) -> ListNode:\n",
    "        p1 = ListNode(-1)\n",
    "        p2 = ListNode(-1)\n",
    "        cur1 = p1\n",
    "        cur2 = p2\n",
    "        while head:\n",
    "            if head.val < x:\n",
    "                cur1.next = head\n",
    "                cur1 = cur1.next\n",
    "            else:\n",
    "                cur2.next = head\n",
    "                cur2 = cur2.next\n",
    "            temp = head.next\n",
    "            head.next = None\n",
    "            head = temp\n",
    "        cur1.next = p2.next\n",
    "        return p1.next"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "from typing import List\n",
    "import collections\n",
    "\n",
    "# Definition for singly-linked list.\n",
    "# class ListNode:\n",
    "#     def __init__(self, x):\n",
    "#         self.val = x\n",
    "#         self.next = None\n",
    "\n",
    "class Solution:\n",
    "    def partition(self, head: ListNode, x: int) -> ListNode:\n",
    "        a, b = ListNode(0), ListNode(0)\n",
    "        m, n = a, b\n",
    "        while head:\n",
    "            if head.val < x:\n",
    "                m.next = head\n",
    "                m = m.next\n",
    "            else:\n",
    "                n.next = head\n",
    "                n = n.next\n",
    "            head = head.next\n",
    "        n.next = None\n",
    "        m.next = b.next\n",
    "        return a.next\n",
    "            \n"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "from typing import List\n",
    "import collections\n",
    "\n",
    "\"\"\"\n",
    "[3,5,8,5,10,2,1]\n",
    "5\n",
    "[1,4,3,2,5,2]\n",
    "3\n",
    "[]\n",
    "0\n",
    "\n",
    "\"\"\"\n",
    "\n",
    "# Definition for singly-linked list.\n",
    "# class ListNode:\n",
    "#     def __init__(self, x):\n",
    "#         self.val = x\n",
    "#         self.next = None\n",
    "\n",
    "class Solution:\n",
    "    def partition(self, head: ListNode, x: int) -> ListNode:\n",
    "        _smaller = ListNode()\n",
    "        smaller = _smaller\n",
    "        bigger = head\n",
    "        _biggerPre = ListNode()\n",
    "        biggerPre = _biggerPre\n",
    "        biggerPre.next = bigger\n",
    "        while bigger:\n",
    "            if bigger.val < x:\n",
    "                smaller.next = bigger\n",
    "                smaller = smaller.next\n",
    "                biggerPre.next = bigger.next\n",
    "            else:\n",
    "                biggerPre = bigger\n",
    "            bigger = bigger.next\n",
    "\n",
    "        smaller.next = _biggerPre.next\n",
    "        return _smaller.next"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "from typing import List\n",
    "import collections\n",
    "\n",
    "# Definition for singly-linked list.\n",
    "# class ListNode:\n",
    "#     def __init__(self, x):\n",
    "#         self.val = x\n",
    "#         self.next = None\n",
    "\n",
    "class Solution:\n",
    "    def partition(self, head: ListNode, x: int) -> ListNode:\n",
    "        op1, op2 = ListNode(0), ListNode(0)\n",
    "        p1 = op1\n",
    "        p2 = op2\n",
    "        op = head\n",
    "        while op:\n",
    "            if op.val >= x:\n",
    "                op2.next = op\n",
    "                op2 = op\n",
    "            else:\n",
    "                op1.next = op\n",
    "                op1 = op\n",
    "            op = op.next\n",
    "        op2.next = None\n",
    "        op1.next = p2.next\n",
    "        return p1.next\n",
    "            "
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "from typing import List\n",
    "import collections\n",
    "\n",
    "class Solution:\n",
    "    def partition(self, head: ListNode, x: int) -> ListNode:\n",
    "        p, q = head, head\n",
    "        while q:\n",
    "            if q.val < x:\n",
    "                p.val, q.val = q.val, p.val\n",
    "                p = p.next\n",
    "            q = q.next\n",
    "        return head"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "from typing import List\n",
    "import collections\n",
    "\n",
    "# Definition for singly-linked list.\n",
    "# class ListNode:\n",
    "#     def __init__(self, x):\n",
    "#         self.val = x\n",
    "#         self.next = None\n",
    "\n",
    "class Solution:\n",
    "    def partition(self, head: ListNode, x: int) -> ListNode:\n",
    "        bigger = ListNode(-1)\n",
    "        smaller = ListNode(-1)\n",
    "        smaller.next = head\n",
    "        dummy = smaller\n",
    "        dummy_1 = bigger\n",
    "        while smaller and smaller.next:\n",
    "            if smaller.next.val >= x:\n",
    "                temp = smaller.next\n",
    "                smaller.next = smaller.next.next\n",
    "                temp.next = None\n",
    "                bigger.next = temp\n",
    "                bigger = bigger.next\n",
    "            else:\n",
    "                smaller = smaller.next\n",
    "        smaller.next = dummy_1.next\n",
    "        return dummy.next"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "from typing import List\n",
    "import collections\n",
    "\n",
    "# Definition for singly-linked list.\n",
    "# class ListNode:\n",
    "#     def __init__(self, x):\n",
    "#         self.val = x\n",
    "#         self.next = None\n",
    "\n",
    "class Solution:\n",
    "    def partition(self, head: ListNode, x: int) -> ListNode:\n",
    "        smallHead, largeHead = ListNode(), ListNode()\n",
    "        small, large = smallHead, largeHead\n",
    "        while head != None:\n",
    "            if head.val >= x:\n",
    "                large.next = head\n",
    "                large = large.next\n",
    "            else:\n",
    "                small.next = head\n",
    "                small = small.next\n",
    "            head = head.next\n",
    "        large.next = None\n",
    "        small.next = largeHead.next\n",
    "        return smallHead.next"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "from typing import List\n",
    "import collections\n",
    "\n",
    "# Definition for singly-linked list.\n",
    "# class ListNode:\n",
    "#     def __init__(self, x):\n",
    "#         self.val = x\n",
    "#         self.next = None\n",
    "\n",
    "class Solution:\n",
    "    def partition(self, head: ListNode, x: int) -> ListNode:\n",
    "        pseudo_head = ListNode(next=head)\n",
    "\n",
    "        cur = pseudo_head\n",
    "        while cur and cur.next :\n",
    "            if cur.next.val < x:\n",
    "                if cur != pseudo_head:\n",
    "                    tmp = cur.next.next \n",
    "                    cur.next.next = pseudo_head.next \n",
    "                    pseudo_head.next = cur.next\n",
    "                    cur.next = tmp \n",
    "                else:\n",
    "                    cur = cur.next \n",
    "            else:\n",
    "                cur = cur.next \n",
    "        \n",
    "        return pseudo_head.next "
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "from typing import List\n",
    "import collections\n",
    "\n",
    "# Definition for singly-linked list.\n",
    "# class ListNode:\n",
    "#     def __init__(self, x):\n",
    "#         self.val = x\n",
    "#         self.next = None\n",
    "\n",
    "class Solution:\n",
    "    def partition(self, head: ListNode, x: int) -> ListNode:\n",
    "        small = ListNode(0)\n",
    "        small_head = small\n",
    "        large = ListNode(0)\n",
    "        large_head = large\n",
    "        \n",
    "        while head:\n",
    "            if head.val < x:\n",
    "                small.next = head\n",
    "                small = small.next\n",
    "            else:\n",
    "                large.next = head\n",
    "                large = large.next\n",
    "            head = head.next\n",
    "        \n",
    "        # This is important to prevent a cycle in the linked list.\n",
    "        large.next = None\n",
    "        \n",
    "        # Connect the small list with the large list\n",
    "        small.next = large_head.next\n",
    "        \n",
    "        return small_head.next"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "from typing import List\n",
    "import collections\n",
    "\n",
    "# Definition for singly-linked list.\n",
    "# class ListNode:\n",
    "#     def __init__(self, x):\n",
    "#         self.val = x\n",
    "#         self.next = None\n",
    "\n",
    "class Solution:\n",
    "    def partition(self, head: ListNode, x: int) -> ListNode:\n",
    "        lesscur = less = ListNode()\n",
    "        morecur = more = ListNode()\n",
    "        while head:\n",
    "            if head.val < x:\n",
    "                lesscur.next  = head\n",
    "                lesscur = lesscur.next\n",
    "                head = head.next\n",
    "            else:\n",
    "                morecur.next = head\n",
    "                morecur = morecur.next\n",
    "                head = head.next\n",
    "        lesscur.next = more.next\n",
    "        morecur.next = None\n",
    "        return less.next"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "from typing import List\n",
    "import collections\n",
    "\n",
    "\"\"\"\n",
    "[3,5,8,5,10,2,1]\n",
    "5\n",
    "[1,4,3,2,5,2]\n",
    "3\n",
    "[]\n",
    "0\n",
    "\n",
    "\"\"\"\n",
    "\n",
    "# Definition for singly-linked list.\n",
    "# class ListNode:\n",
    "#     def __init__(self, x):\n",
    "#         self.val = x\n",
    "#         self.next = None\n",
    "\n",
    "class Solution:\n",
    "    \"\"\"\n",
    "    def partition(self, head: ListNode, x: int) -> ListNode:\n",
    "        _smaller = ListNode()\n",
    "        smaller = _smaller\n",
    "        bigger = head\n",
    "        _biggerPre = ListNode()\n",
    "        biggerPre = _biggerPre\n",
    "        biggerPre.next = bigger\n",
    "        while bigger:\n",
    "            if bigger.val < x:\n",
    "                smaller.next = bigger\n",
    "                smaller = smaller.next\n",
    "                biggerPre.next = bigger.next\n",
    "            else:\n",
    "                biggerPre = bigger\n",
    "            bigger = bigger.next\n",
    "\n",
    "        smaller.next = _biggerPre.next\n",
    "        return _smaller.next\n",
    "    \"\"\"\n",
    "    def partition(self, head: ListNode, x: int) -> ListNode:\n",
    "        _less, _greater = ListNode(), ListNode()\n",
    "        less, greater = _less, _greater\n",
    "\n",
    "        while head:\n",
    "            if head.val < x:\n",
    "                less.next = head\n",
    "                less = less.next\n",
    "            else:\n",
    "                greater.next = head\n",
    "                greater = greater.next\n",
    "            head = head.next\n",
    "\n",
    "        less.next = _greater.next\n",
    "        greater.next = None\n",
    "        return _less.next"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "from typing import List\n",
    "import collections\n",
    "\n",
    "# Definition for singly-linked list.\n",
    "# class ListNode:\n",
    "#     def __init__(self, x):\n",
    "#         self.val = x\n",
    "#         self.next = None\n",
    "\n",
    "class Solution:\n",
    "    def partition(self, head: ListNode, x: int) -> ListNode:\n",
    "        f,rot=0,ListNode(0);rot.next=head\n",
    "        while(head):f+=(head.val<x);head=head.next\n",
    "        if(not f):return rot.next\n",
    "        head,g,h=rot.next,f,0\n",
    "        while(f):f-=1;head=head.next\n",
    "        if(not head):return rot.next\n",
    "        head1=rot.next\n",
    "        while(h<g):\n",
    "            while(h<g and head1.val<x):h+=1;head1=head1.next\n",
    "            while(h<g and head.val>=x):head=head.next\n",
    "            head1.val,head.val=head.val,head1.val\n",
    "        return rot.next"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "from typing import List\n",
    "import collections\n",
    "\n",
    "# Definition for singly-linked list.\n",
    "# class ListNode:\n",
    "#     def __init__(self, x):\n",
    "#         self.val = x\n",
    "#         self.next = None\n",
    "\n",
    "class Solution:\n",
    "    def partition(self, head: ListNode, x: int) -> ListNode:\n",
    "        if head is None:\n",
    "            return None\n",
    "        \n",
    "        lts = []\n",
    "        gts = []\n",
    "        pos = head\n",
    "        while pos:\n",
    "            if pos.val < x:\n",
    "                lts.append(pos)\n",
    "            else:\n",
    "                gts.append(pos)\n",
    "            pos = pos.next\n",
    "        \n",
    "        nodes = lts + gts\n",
    "        pos = res = nodes[0]\n",
    "        for node in nodes[1:]:\n",
    "            pos.next = node\n",
    "            pos = pos.next\n",
    "        pos.next = None\n",
    "        \n",
    "        return res"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "from typing import List\n",
    "import collections\n",
    "\n",
    "# Definition for singly-linked list.\n",
    "# class ListNode:\n",
    "#     def __init__(self, x):\n",
    "#         self.val = x\n",
    "#         self.next = None\n",
    "\n",
    "class Solution:\n",
    "    def partition(self, head: ListNode, x: int) -> ListNode:\n",
    "        dummy1=ListNode()\n",
    "        dummy2=ListNode()\n",
    "        cur1=dummy1\n",
    "        cur2=dummy2\n",
    "        cur=head\n",
    "        while cur:\n",
    "            if cur.val<x:\n",
    "                cur1.next=cur\n",
    "                cur1=cur1.next\n",
    "            else:\n",
    "                cur2.next=cur\n",
    "                cur2=cur2.next\n",
    "            cur=cur.next\n",
    "        cur1.next=dummy2.next\n",
    "        cur2.next=None\n",
    "        return dummy1.next\n",
    "        \n",
    "\n",
    "\n",
    "\n",
    "        "
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "from typing import List\n",
    "import collections\n",
    "\n",
    "# Definition for singly-linked list.\n",
    "# class ListNode:\n",
    "#     def __init__(self, x):\n",
    "#         self.val = x\n",
    "#         self.next = None\n",
    "\n",
    "class Solution:\n",
    "    def partition(self, head: ListNode, x: int) -> ListNode:\n",
    "        sml_dummy,big_dummy=ListNode(0),ListNode(0)\n",
    "        #保持头部节点不变，后续移动使用辅助指针节点，很方便！！！！！！！！！！！！1\n",
    "        sml,big=sml_dummy,big_dummy\n",
    "        while head:\n",
    "            #将<x的节点加入sml\n",
    "            if head.val<x:\n",
    "                sml.next=head\n",
    "                sml=sml.next\n",
    "            #将>=x的节点加入Big\n",
    "            else:\n",
    "                big.next=head\n",
    "                big=big.next\n",
    "            head=head.next\n",
    "        #拼接两个链表\n",
    "        sml.next=big_dummy.next\n",
    "        big.next=None\n",
    "        return sml_dummy.next\n",
    "\n"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "from typing import List\n",
    "import collections\n",
    "\n",
    "# Definition for singly-linked list.\n",
    "# class ListNode:\n",
    "#     def __init__(self, x):\n",
    "#         self.val = x\n",
    "#         self.next = None\n",
    "\n",
    "class Solution:\n",
    "    def partition(self, head: ListNode, x: int) -> ListNode:\n",
    "        dummyLess = ListNode(-1)\n",
    "        dummyMore = ListNode(-2)\n",
    "\n",
    "        curLess = dummyLess\n",
    "        curMore = dummyMore\n",
    "\n",
    "        while head:\n",
    "            if head.val < x:\n",
    "                curLess.next = head\n",
    "                curLess = curLess.next\n",
    "            else:\n",
    "                curMore.next = head\n",
    "                curMore = curMore.next\n",
    "            head = head.next\n",
    "        curMore.next = None\n",
    "        curLess.next = dummyMore.next\n",
    "        return dummyLess.next"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "from typing import List\n",
    "import collections\n",
    "\n",
    "# Definition for singly-linked list.\n",
    "# class ListNode:\n",
    "#     def __init__(self, x):\n",
    "#         self.val = x\n",
    "#         self.next = None\n",
    "\n",
    "class Solution:\n",
    "    def partition(self, head: ListNode, x: int) -> ListNode:\n",
    "        part1, part2 = [], []\n",
    "        while head:\n",
    "            if head.val < x:\n",
    "                part1.append(head.val)\n",
    "            else:\n",
    "                part2.append(head.val)\n",
    "            head = head.next\n",
    "        dummy = ListNode(0)\n",
    "        prev = dummy\n",
    "        for i in range(len(part1)):\n",
    "            prev.next = ListNode(part1[i])\n",
    "            prev = prev.next\n",
    "        for j in range(len(part2)):\n",
    "            prev.next = ListNode(part2[j])\n",
    "            prev = prev.next\n",
    "        return dummy.next"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "from typing import List\n",
    "import collections\n",
    "\n",
    "# Definition for singly-linked list.\n",
    "# class ListNode:\n",
    "#     def __init__(self, x):\n",
    "#         self.val = x\n",
    "#         self.next = None\n",
    "\n",
    "class Solution:\n",
    "    def partition(self, head: ListNode, x: int) -> ListNode:\n",
    "        # p=head\n",
    "        # maxp=p\n",
    "        # maxpnum=-1\n",
    "        # t=0\n",
    "        # p0=None\n",
    "        # maxp0=None\n",
    "        # ll=[]\n",
    "        # bz=True\n",
    "        # fpp=ListNode(9)\n",
    "        # fpp.next=head\n",
    "        # maxp0=fpp\n",
    "        # p0=fpp\n",
    "        # while p is not None:\n",
    "        #     print(p.val)\n",
    "        #     if bz and p.val>=x:\n",
    "\n",
    "        #         maxp=p\n",
    "        #         maxpnum=t\n",
    "        #         maxp0=p0\n",
    "        #         bz=False\n",
    "        #     if p.val<x and t>maxpnum and maxpnum>-1:\n",
    "        #         print('ppp',p.val,p0.val,maxp0)\n",
    "        #         if not bz:\n",
    "        #             p0.next=p.next\n",
    "        #             p.next=maxp\n",
    "        #             maxp0.next=p\n",
    "        #             maxp0=p\n",
    "        #             p=p0.next\n",
    "        #             # if t==1:\n",
    "        #             #     head=maxp0.next\n",
    "        #             #     print(head.val)\n",
    "                \n",
    "        #         else:\n",
    "        #             ll.append(p)\n",
    "        #             p0.next=p.next\n",
    "        #             p=p0.next\n",
    "        #         print('ppp2',p,p0)\n",
    "        #         continue\n",
    "        #     t+=1\n",
    "        #     p0=p\n",
    "        #     p=p.next\n",
    "        # print(head)\n",
    "        # if maxp0 is not None:\n",
    "        #     for i in range(len(ll)):\n",
    "        #         pp=maxp0.next\n",
    "        #         maxp0.next=ll[i]\n",
    "        #         maxp0.next.next=pp\n",
    "        \n",
    "        # return maxp0\n",
    "\n",
    "        p=head\n",
    "        m=[]\n",
    "        maxnum=-1\n",
    "        t=0\n",
    "        \n",
    "        bz=True\n",
    "        maxp=None\n",
    "        tou=ListNode(0)\n",
    "        tou.next=head\n",
    "        p0=tou\n",
    "        while p is not None:\n",
    "            \n",
    "            if p.val>=x and bz:\n",
    "                maxnum=t\n",
    "                maxp=p\n",
    "                bz=False\n",
    "                p0=p\n",
    "                p=p.next\n",
    "                t+=1\n",
    "\n",
    "                continue\n",
    "            print(p.val,t)\n",
    "            if p.val<x:\n",
    "                m.append(p)\n",
    "                p0.next=p.next\n",
    "                p=p.next\n",
    "                t=t+1\n",
    "                \n",
    "                if p is None:\n",
    "                    break\n",
    "                print('====',p.val,p0.val)\n",
    "                continue\n",
    "            \n",
    "            t+=1\n",
    "            p0=p\n",
    "            p=p.next\n",
    "\n",
    "        for i in range(len(m)):\n",
    "            y=tou.next\n",
    "            tou.next=m[i]\n",
    "            m[i].next=y\n",
    "        return tou.next"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "from typing import List\n",
    "import collections\n",
    "\n",
    "# Definition for singly-linked list.\n",
    "# class ListNode:\n",
    "#     def __init__(self, x):\n",
    "#         self.val = x\n",
    "#         self.next = None\n",
    "\n",
    "class Solution:\n",
    "    def partition(self, head: ListNode, x: int) -> ListNode:\n",
    "        if head is None:\n",
    "            return head\n",
    "\n",
    "        curr = head\n",
    "\n",
    "        # 存放比x小的值的链表头\n",
    "        ltx = ListNode(-101)\n",
    "        curr_ltx = ltx\n",
    "        # 存放比x大的值的链表头\n",
    "        gtx = ListNode(-101)\n",
    "        curr_gtx = gtx\n",
    "\n",
    "        while curr is not None:\n",
    "            next_node = curr.next\n",
    "            curr.next = None\n",
    "            if curr.val < x:\n",
    "                curr_ltx.next = curr\n",
    "                curr_ltx = curr_ltx.next\n",
    "                curr = next_node\n",
    "            else:\n",
    "                curr_gtx.next = curr\n",
    "                curr_gtx = curr_gtx.next\n",
    "            curr = next_node\n",
    "\n",
    "        curr_ltx.next = gtx.next\n",
    "        return ltx.next\n"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "from typing import List\n",
    "import collections\n",
    "\n",
    "# Definition for singly-linked list.\n",
    "# class ListNode:\n",
    "#     def __init__(self, x):\n",
    "#         self.val = x\n",
    "#         self.next = None\n",
    "\n",
    "class Solution:\n",
    "    def partition(self, head: ListNode, x: int) -> ListNode:\n",
    "\n",
    "        # 新建两个链表分别存储\n",
    "        smalldummy = ListNode()\n",
    "        largedummy = ListNode()\n",
    "        sml,big = smalldummy,largedummy\n",
    "        # 遍历\n",
    "        while head:\n",
    "            if head.val < x:\n",
    "                sml.next = head\n",
    "                sml = sml.next\n",
    "            else:\n",
    "                big.next = head\n",
    "                big = big.next\n",
    "            head = head.next\n",
    "\n",
    "        sml.next = largedummy.next\n",
    "        big.next = None\n",
    "        return smalldummy.next\n",
    "                \n"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "from typing import List\n",
    "import collections\n",
    "\n",
    "# Definition for singly-linked list.\n",
    "# class ListNode:\n",
    "#     def __init__(self, x):\n",
    "#         self.val = x\n",
    "#         self.next = None\n",
    "\n",
    "class Solution:\n",
    "    def partition(self, head: ListNode, x: int) -> ListNode:\n",
    "        # 把小于x的提出来\n",
    "        d1 = ListNode()\n",
    "        d2 = ListNode()\n",
    "        r1, r2 = d1, d2\n",
    "        p = head\n",
    "        while p is not None:\n",
    "            # print(p.val)\n",
    "            if p.val < x:\n",
    "                r1.next = p\n",
    "                r1 = r1.next\n",
    "            else:\n",
    "                r2.next = p\n",
    "                r2 = r2.next\n",
    "            p = p.next\n",
    "        r2.next = None\n",
    "        r1.next = d2.next\n",
    "        return d1.next"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "from typing import List\n",
    "import collections\n",
    "\n",
    "\n",
    "class Solution:\n",
    "    def partition(self, head: ListNode, x: int) -> ListNode:\n",
    "        node = head\n",
    "        while node:\n",
    "            if node.val >= x:\n",
    "                cur = node.next\n",
    "                while cur and cur.val >= x:\n",
    "                    cur = cur.next\n",
    "                if cur:\n",
    "                    cur.val, node.val = node.val, cur.val\n",
    "                else:\n",
    "                    break\n",
    "            node = node.next\n",
    "        return head"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "from typing import List\n",
    "import collections\n",
    "\n",
    "# Definition for singly-linked list.\n",
    "# class ListNode:\n",
    "#     def __init__(self, x):\n",
    "#         self.val = x\n",
    "#         self.next = None\n",
    "\n",
    "class Solution:\n",
    "    def partition(self, head: ListNode, x: int) -> ListNode:\n",
    "        virtual = ListNode(0)\n",
    "        virtual.next = head\n",
    "        head1, head2 = virtual, head\n",
    "        while head2 != None:\n",
    "            if head2.val >= x:\n",
    "                head2 = head2.next\n",
    "                head1 = head1.next\n",
    "            else:\n",
    "                temp = head2\n",
    "                head2 = head2.next\n",
    "                head1.next = head2\n",
    "                temp.next = virtual.next\n",
    "                virtual.next = temp\n",
    "                while head1.next != head2:\n",
    "                    head1 = head1.next\n",
    "        return virtual.next"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "from typing import List\n",
    "import collections\n",
    "\n",
    "# Definition for singly-linked list.\n",
    "# class ListNode:\n",
    "#     def __init__(self, x):\n",
    "#         self.val = x\n",
    "#         self.next = None\n",
    "\n",
    "class Solution:\n",
    "    def partition(self, head: ListNode, x: int) -> ListNode:\n",
    "        # s1 = []\n",
    "        # while head:\n",
    "        #     s1.append(head.val)\n",
    "        #     head = head.next\n",
    "        \n",
    "        # s2 = []\n",
    "        # s3 = []\n",
    "        # for i in range(len(s1)):\n",
    "        #     if s1[i] < x:\n",
    "        #         s2.append(s1[i])\n",
    "        #     else:\n",
    "        #         s3.append(s1[i])\n",
    "        # s = s2 + s3\n",
    "        \n",
    "        # pre = cur = ListNode(0)\n",
    "        # for i in s:\n",
    "        #     pre.next = ListNode(i)\n",
    "        #     pre = pre.next\n",
    "\n",
    "        # return cur.next\n",
    "        \n",
    "        s1 = []\n",
    "        s2 = []\n",
    "        while head:\n",
    "            if head.val < x:\n",
    "                s1.append(head.val)\n",
    "            else:\n",
    "                s2.append(head.val)\n",
    "            head = head.next\n",
    "\n",
    "        s = s1 + s2\n",
    "        \n",
    "        pre = cur = ListNode(0)\n",
    "        for i in s:\n",
    "            pre.next = ListNode(i)\n",
    "            pre = pre.next\n",
    "\n",
    "        return cur.next"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "from typing import List\n",
    "import collections\n",
    "\n",
    "# Definition for singly-linked list.\n",
    "# class ListNode:\n",
    "#     def __init__(self, x):\n",
    "#         self.val = x\n",
    "#         self.next = None\n",
    "\n",
    "class Solution:\n",
    "    def partition(self, head: ListNode, x: int) -> ListNode:\n",
    "        small, large = ListNode(0), ListNode(0)\n",
    "        l = large\n",
    "        s = small\n",
    "        cur = head\n",
    "        while cur:\n",
    "            if cur.val >= x:\n",
    "                large.next = ListNode(cur.val)\n",
    "                large = large.next\n",
    "            else:\n",
    "                small.next = ListNode(cur.val)\n",
    "                small =  small.next\n",
    "            cur = cur.next\n",
    "        small.next = l.next\n",
    "        return s.next\n",
    "                "
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "from typing import List\n",
    "import collections\n",
    "\n",
    "class Solution:\n",
    "    def partition(self, head: ListNode, x: int) -> ListNode:\n",
    "        dummy = ListNode(-1)\n",
    "        node = dummy\n",
    "        node.next = head\n",
    "        while node.next != None:\n",
    "            if node.next.val < x:\n",
    "                node = node.next\n",
    "            else:\n",
    "                cur = node\n",
    "                while cur.next and cur.next.val >= x:\n",
    "                    cur = cur.next\n",
    "                if cur.next:\n",
    "                    if node.next == cur:\n",
    "                        next = cur.next\n",
    "                        cur.next = next.next\n",
    "                        next.next = cur\n",
    "                        node.next = next\n",
    "                    else:\n",
    "                        next = node.next\n",
    "                        node.next = cur.next\n",
    "                        nn = next.next\n",
    "                        next.next = cur.next.next\n",
    "                        cur.next = next\n",
    "                        node.next.next = nn\n",
    "                        node = node.next\n",
    "                else:\n",
    "                    break\n",
    "        return dummy.next\n",
    "\n"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "from typing import List\n",
    "import collections\n",
    "\n",
    "# Definition for singly-linked list.\n",
    "# class ListNode:\n",
    "#     def __init__(self, x):\n",
    "#         self.val = x\n",
    "#         self.next = None\n",
    "\n",
    "class Solution:\n",
    "    def partition(self, head: ListNode, x: int) -> ListNode:\n",
    "        pseudo_head = ListNode(next=head)\n",
    "\n",
    "        cur = pseudo_head\n",
    "        while cur and cur.next :\n",
    "            if cur.next.val < x:\n",
    "                if cur != pseudo_head:\n",
    "                    tmp = cur.next.next \n",
    "                    cur.next.next = pseudo_head.next \n",
    "                    pseudo_head.next = cur.next\n",
    "                    cur.next = tmp \n",
    "                else:\n",
    "                    cur = cur.next \n",
    "            else:\n",
    "                cur = cur.next \n",
    "        \n",
    "        return pseudo_head.next "
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "from typing import List\n",
    "import collections\n",
    "\n",
    "# Definition for singly-linked list.\n",
    "# class ListNode:\n",
    "#     def __init__(self, x):\n",
    "#         self.val = x\n",
    "#         self.next = None\n",
    "\n",
    "class Solution:\n",
    "    def partition(self, head: ListNode, x: int) -> ListNode:\n",
    "        small=smallHead=ListNode()\n",
    "        big=bigHead=ListNode()\n",
    "        cur=head\n",
    "        while cur:\n",
    "            if cur.val<x:\n",
    "                small.next=cur\n",
    "                small=small.next\n",
    "            else:\n",
    "                big.next=cur\n",
    "                big=big.next\n",
    "            cur=cur.next\n",
    "        big.next=None\n",
    "        small.next=bigHead.next\n",
    "        return smallHead.next\n"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "from typing import List\n",
    "import collections\n",
    "\n",
    "# Definition for singly-linked list.\n",
    "# class ListNode:\n",
    "#     def __init__(self, x):\n",
    "#         self.val = x\n",
    "#         self.next = None\n",
    "\n",
    "class Solution:\n",
    "    def partition(self, head: ListNode, x: int) -> ListNode:\n",
    "        small_dummy, big_dummy = ListNode(), ListNode()\n",
    "        sml, big = small_dummy, big_dummy\n",
    "        while head:\n",
    "            if head.val < x:\n",
    "                sml.next = head\n",
    "                sml = sml.next\n",
    "            else:\n",
    "                big.next = head\n",
    "                big = big.next\n",
    "            head = head.next\n",
    "        sml.next = big_dummy.next\n",
    "        big.next = None\n",
    "        return small_dummy.next"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "from typing import List\n",
    "import collections\n",
    "\n",
    "# Definition for singly-linked list.\n",
    "# class ListNode:\n",
    "#     def __init__(self, x):\n",
    "#         self.val = x\n",
    "#         self.next = None\n",
    "\n",
    "class Solution:\n",
    "    def partition(self, head: ListNode, x: int) -> ListNode:\n",
    "        temp = ListNode() # 空节点承受所有\n",
    "        tail = temp\n",
    "\n",
    "        kong = ListNode()\n",
    "        kong.next = head\n",
    "\n",
    "        pre = kong\n",
    "        cur = head\n",
    "        \n",
    "        while cur:\n",
    "            value = cur.val\n",
    "            if value<x:\n",
    "                pre.next = cur.next\n",
    "                cur.next = tail.next\n",
    "                tail.next = cur\n",
    "                tail = tail.next\n",
    "                cur = pre.next\n",
    "            else:\n",
    "                pre = pre.next\n",
    "                cur = cur.next\n",
    "        tail.next  = kong.next\n",
    "        return temp.next\n"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "from typing import List\n",
    "import collections\n",
    "\n",
    "# Definition for singly-linked list.\n",
    "# class ListNode:\n",
    "#     def __init__(self, x):\n",
    "#         self.val = x\n",
    "#         self.next = None\n",
    "\n",
    "class Solution:\n",
    "    def partition(self, head: ListNode, x: int) -> ListNode:\n",
    "        l1,l2 = ListNode(0),ListNode(0)\n",
    "        a,b = l1,l2\n",
    "        while head:\n",
    "            if head.val < x:\n",
    "                a.next = head\n",
    "                a = a.next\n",
    "            else:\n",
    "                b.next = head\n",
    "                b = b.next\n",
    "            head = head.next\n",
    "        \n",
    "        a.next = l2.next\n",
    "        b.next = None\n",
    "        return l1.next\n",
    "\n"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "from typing import List\n",
    "import collections\n",
    "\n",
    "# Definition for singly-linked list.\n",
    "# class ListNode:\n",
    "#     def __init__(self, x):\n",
    "#         self.val = x\n",
    "#         self.next = None\n",
    "\n",
    "class Solution:\n",
    "    def partition(self, head: ListNode, x: int) -> ListNode:\n",
    "        hair = ListNode(-1, head)\n",
    "        p_small = ListNode(-1)\n",
    "        p_other = ListNode(-1)\n",
    "        p, ps, po = hair, p_small, p_other\n",
    "        while p.next:\n",
    "            p = p.next\n",
    "            if p.val < x:\n",
    "                ps.next = p\n",
    "                ps = ps.next\n",
    "            else: \n",
    "                po.next = p \n",
    "                po = po.next\n",
    "        po.next = None  # key of this problem: remove previous connections\n",
    "        ps.next = p_other.next\n",
    "        return p_small.next"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "from typing import List\n",
    "import collections\n",
    "\n",
    "# Definition for singly-linked list.\n",
    "# class ListNode:\n",
    "#     def __init__(self, x):\n",
    "#         self.val = x\n",
    "#         self.next = None\n",
    "\n",
    "class Solution:\n",
    "    def partition(self, head: ListNode, x: int) -> ListNode:\n",
    "        if not head:\n",
    "            return None\n",
    "        dummySmall = ListNode(val = 0, next = None)\n",
    "        dummyBig = ListNode(val = 0, next = None)\n",
    "        smallTail, bigTail = dummySmall, dummyBig\n",
    "        while head:\n",
    "            nextNode = head.next\n",
    "            head.next = None\n",
    "            if head.val < x:\n",
    "                smallTail.next = head\n",
    "                smallTail = smallTail.next\n",
    "            else:\n",
    "                bigTail.next = head\n",
    "                bigTail = bigTail.next\n",
    "            head = nextNode\n",
    "        smallTail.next = dummyBig.next\n",
    "        return dummySmall.next"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "from typing import List\n",
    "import collections\n",
    "\n",
    "# Definition for singly-linked list.\n",
    "# class ListNode:\n",
    "#     def __init__(self, x):\n",
    "#         self.val = x\n",
    "#         self.next = None\n",
    "\n",
    "class Solution:\n",
    "    def partition(self, head: ListNode, x: int) -> ListNode:\n",
    "        pseudo_head = ListNode(next=head)\n",
    "\n",
    "        cur = pseudo_head\n",
    "        while cur and cur.next :\n",
    "            if cur.next.val < x:\n",
    "                if cur != pseudo_head:\n",
    "                    tmp = cur.next.next \n",
    "                    cur.next.next = pseudo_head.next \n",
    "                    pseudo_head.next = cur.next\n",
    "                    cur.next = tmp \n",
    "                else:\n",
    "                    cur = cur.next \n",
    "            else:\n",
    "                cur = cur.next \n",
    "        \n",
    "        return pseudo_head.next "
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "from typing import List\n",
    "import collections\n",
    "\n",
    "# Definition for singly-linked list.\n",
    "# class ListNode:\n",
    "#     def __init__(self, x):\n",
    "#         self.val = x\n",
    "#         self.next = None\n",
    "\n",
    "class Solution:\n",
    "    def partition(self, head: ListNode, x: int) -> ListNode:\n",
    "        sml_dummy, big_dummy = ListNode(0), ListNode(0)\n",
    "        sml, big = sml_dummy, big_dummy\n",
    "        while head:\n",
    "            if head.val < x:\n",
    "                sml.next = head\n",
    "                sml = sml.next\n",
    "            else:\n",
    "                big.next = head\n",
    "                big = big.next\n",
    "            head = head.next\n",
    "        sml.next = big_dummy.next\n",
    "        big.next = None\n",
    "        return sml_dummy.next\n"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "from typing import List\n",
    "import collections\n",
    "\n",
    "# Definition for singly-linked list.\n",
    "# class ListNode:\n",
    "#     def __init__(self, x):\n",
    "#         self.val = x\n",
    "#         self.next = None\n",
    "\n",
    "class Solution:\n",
    "    def partition(self, head: ListNode, x: int) -> ListNode:\n",
    "        pseudo_head = ListNode(next=head)\n",
    "\n",
    "        cur = pseudo_head\n",
    "        while cur and cur.next :\n",
    "            if cur.next.val < x:\n",
    "                if cur != pseudo_head:\n",
    "                    tmp = cur.next.next \n",
    "                    cur.next.next = pseudo_head.next \n",
    "                    pseudo_head.next = cur.next\n",
    "                    cur.next = tmp \n",
    "                else:\n",
    "                    cur = cur.next \n",
    "            else:\n",
    "                cur = cur.next \n",
    "        \n",
    "        return pseudo_head.next "
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "from typing import List\n",
    "import collections\n",
    "\n",
    "# Definition for singly-linked list.\n",
    "# class ListNode:\n",
    "#     def __init__(self, x):\n",
    "#         self.val = x\n",
    "#         self.next = None\n",
    "\n",
    "class Solution:\n",
    "    def partition(self, head: ListNode, x: int) -> ListNode:\n",
    "        small = ListNode(-1)\n",
    "        big = ListNode(-1)\n",
    "        small_pre = small\n",
    "        big_pre = big\n",
    "        cur = head\n",
    "        while cur:\n",
    "            tmp = cur.next\n",
    "            cur.next = None\n",
    "            if cur.val < x:\n",
    "                small_pre.next = cur\n",
    "                small_pre = small_pre.next\n",
    "            else:\n",
    "                big_pre.next = cur\n",
    "                big_pre = big_pre.next\n",
    "            cur = tmp\n",
    "        small_pre.next = big.next\n",
    "        return small.next\n",
    "        \n",
    "        "
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "from typing import List\n",
    "import collections\n",
    "\n",
    "# Definition for singly-linked list.\n",
    "# class ListNode:\n",
    "#     def __init__(self, x):\n",
    "#         self.val = x\n",
    "#         self.next = None\n",
    "\n",
    "class Solution:\n",
    "    def partition(self, head: ListNode, x: int) -> ListNode:\n",
    "        a = ListNode(0)\n",
    "        b = ListNode(0)\n",
    "        p1, p2 = a, b\n",
    "        while head:\n",
    "            if head.val < x:\n",
    "                a.next = head\n",
    "                a = a.next\n",
    "            else:\n",
    "                b.next = head\n",
    "                b = b.next\n",
    "            v = head.next\n",
    "            head.next = None\n",
    "            head = v\n",
    "        a.next = p2.next\n",
    "        return p1.next"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "from typing import List\n",
    "import collections\n",
    "\n",
    "# Definition for singly-linked list.\n",
    "# class ListNode:\n",
    "#     def __init__(self, x):\n",
    "#         self.val = x\n",
    "#         self.next = None\n",
    "\n",
    "class Solution:\n",
    "    def partition(self, head: ListNode, x: int) -> ListNode:\n",
    "        vals = []\n",
    "        cur = head \n",
    "        while cur:\n",
    "            vals.append(cur.val)\n",
    "            cur = cur.next \n",
    "        if not vals:\n",
    "            return \n",
    "        vals.sort()\n",
    "\n",
    "        cur = ListNode(val=vals[0])\n",
    "        pseudo_head = ListNode(val=None, next=cur)\n",
    "        for i in range(1, len(vals)):\n",
    "            cur.next = ListNode(val=vals[i])\n",
    "            cur = cur.next \n",
    "        \n",
    "        return pseudo_head.next \n"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "from typing import List\n",
    "import collections\n",
    "\n",
    "# Definition for singly-linked list.\n",
    "# class ListNode:\n",
    "#     def __init__(self, x):\n",
    "#         self.val = x\n",
    "#         self.next = None\n",
    "\n",
    "class Solution:\n",
    "    def partition(self, head: ListNode, x: int) -> ListNode:\n",
    "        pseudo_head = ListNode(next=head)\n",
    "\n",
    "        cur = pseudo_head\n",
    "        while cur and cur.next :\n",
    "            if cur.next.val < x:\n",
    "                if cur != pseudo_head:\n",
    "                    tmp = cur.next.next \n",
    "                    cur.next.next = pseudo_head.next \n",
    "                    pseudo_head.next = cur.next\n",
    "                    cur.next = tmp \n",
    "                else:\n",
    "                    cur = cur.next \n",
    "            else:\n",
    "                cur = cur.next \n",
    "        \n",
    "        return pseudo_head.next "
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "from typing import List\n",
    "import collections\n",
    "\n",
    "# Definition for singly-linked list.\n",
    "# class ListNode:\n",
    "#     def __init__(self, x):\n",
    "#         self.val = x\n",
    "#         self.next = None\n",
    "\n",
    "class Solution:\n",
    "    def partition(self, head: ListNode, x: int) -> ListNode:\n",
    "        # p=head\n",
    "        # maxp=p\n",
    "        # maxpnum=-1\n",
    "        # t=0\n",
    "        # p0=None\n",
    "        # maxp0=None\n",
    "        # ll=[]\n",
    "        # bz=True\n",
    "        # fpp=ListNode(9)\n",
    "        # fpp.next=head\n",
    "        # maxp0=fpp\n",
    "        # p0=fpp\n",
    "        # while p is not None:\n",
    "        #     print(p.val)\n",
    "        #     if bz and p.val>=x:\n",
    "\n",
    "        #         maxp=p\n",
    "        #         maxpnum=t\n",
    "        #         maxp0=p0\n",
    "        #         bz=False\n",
    "        #     if p.val<x and t>maxpnum and maxpnum>-1:\n",
    "        #         print('ppp',p.val,p0.val,maxp0)\n",
    "        #         if not bz:\n",
    "        #             p0.next=p.next\n",
    "        #             p.next=maxp\n",
    "        #             maxp0.next=p\n",
    "        #             maxp0=p\n",
    "        #             p=p0.next\n",
    "        #             # if t==1:\n",
    "        #             #     head=maxp0.next\n",
    "        #             #     print(head.val)\n",
    "                \n",
    "        #         else:\n",
    "        #             ll.append(p)\n",
    "        #             p0.next=p.next\n",
    "        #             p=p0.next\n",
    "        #         print('ppp2',p,p0)\n",
    "        #         continue\n",
    "        #     t+=1\n",
    "        #     p0=p\n",
    "        #     p=p.next\n",
    "        # print(head)\n",
    "        # if maxp0 is not None:\n",
    "        #     for i in range(len(ll)):\n",
    "        #         pp=maxp0.next\n",
    "        #         maxp0.next=ll[i]\n",
    "        #         maxp0.next.next=pp\n",
    "        \n",
    "        # return maxp0\n",
    "\n",
    "        p=head\n",
    "        m=[]\n",
    "        maxnum=-1\n",
    "        t=0\n",
    "        \n",
    "        bz=True\n",
    "        maxp=None\n",
    "        tou=ListNode(0)\n",
    "        tou.next=head\n",
    "        p0=tou\n",
    "        while p is not None:\n",
    "            \n",
    "            if p.val>=x and bz:\n",
    "                maxnum=t\n",
    "                maxp=p\n",
    "                bz=False\n",
    "                p0=p\n",
    "                p=p.next\n",
    "                t+=1\n",
    "\n",
    "                continue\n",
    "            print(p.val,t)\n",
    "            if p.val<x and t>0:\n",
    "                y=tou.next\n",
    "                p0.next=p.next\n",
    "                # if t>1:\n",
    "                #     p0.next=p.next\n",
    "                q=p\n",
    "                p=p.next\n",
    "                \n",
    "                q.next=y\n",
    "                tou.next=q\n",
    "                \n",
    "                t=t+1\n",
    "                \n",
    "                \n",
    "                # print('====',p.val,p0.val)\n",
    "                continue\n",
    "            \n",
    "            t+=1\n",
    "            p0=p\n",
    "            p=p.next\n",
    "\n",
    "        # for i in range(len(m)):\n",
    "        #     y=tou.next\n",
    "        #     tou.next=m[i]\n",
    "        #     m[i].next=y\n",
    "        return tou.next"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "from typing import List\n",
    "import collections\n",
    "\n",
    "# Definition for singly-linked list.\n",
    "# class ListNode:\n",
    "#     def __init__(self, x):\n",
    "#         self.val = x\n",
    "#         self.next = None\n",
    "\n",
    "class Solution:\n",
    "    def partition(self, head: ListNode, x: int) -> ListNode:\n",
    "        pseudo_head = ListNode(next=head)\n",
    "\n",
    "        cur = pseudo_head\n",
    "        while cur and cur.next :\n",
    "            if cur.next.val < x:\n",
    "                if cur != pseudo_head:\n",
    "                    tmp = cur.next.next \n",
    "                    cur.next.next = pseudo_head.next \n",
    "                    pseudo_head.next = cur.next\n",
    "                    cur.next = tmp \n",
    "                else:\n",
    "                    cur = cur.next \n",
    "            else:\n",
    "                cur = cur.next \n",
    "        \n",
    "        return pseudo_head.next "
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "from typing import List\n",
    "import collections\n",
    "\n",
    "# Definition for singly-linked list.\n",
    "# class ListNode:\n",
    "#     def __init__(self, val=0, next=None):\n",
    "#         self.val = val\n",
    "#         self.next = next\n",
    "class Solution:\n",
    "    def partition(self, head: Optional[ListNode], x: int) -> Optional[ListNode]:\n",
    "        before_head = ListNode(val=-1)\n",
    "        after_head = ListNode(val=-1)\n",
    "\n",
    "        before = before_head\n",
    "        after = after_head\n",
    "\n",
    "        cur = head\n",
    "\n",
    "        while cur:\n",
    "            if cur.val < x:\n",
    "                before.next = cur\n",
    "                before = before.next\n",
    "            else:\n",
    "                after.next = cur\n",
    "                after = after.next\n",
    "            cur = cur.next\n",
    "\n",
    "        before.next = after_head.next\n",
    "        after.next = None\n",
    "\n",
    "        return before_head.next\n",
    "\n",
    "\n",
    "        "
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "from typing import List\n",
    "import collections\n",
    "\n",
    "# Definition for singly-linked list.\n",
    "# class ListNode:\n",
    "#     def __init__(self, x):\n",
    "#         self.val = x\n",
    "#         self.next = None\n",
    "\n",
    "class Solution:\n",
    "    def partition(self, head, x):\n",
    "        \"\"\"\n",
    "        :type head: ListNode\n",
    "        :type x: int\n",
    "        :rtype: ListNode\n",
    "        \"\"\"\n",
    "        l, r = ListNode(0), ListNode(0)\n",
    "        lc, rc = l, r\n",
    "        while head:\n",
    "            n = head\n",
    "            head = head.next\n",
    "            n.next = None\n",
    "            if n.val < x:\n",
    "                lc.next = n\n",
    "                lc = lc.next\n",
    "            else:\n",
    "                rc.next = n\n",
    "                rc = rc.next\n",
    "        lc.next = r.next\n",
    "        return l.next"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "from typing import List\n",
    "import collections\n",
    "\n",
    "# Definition for singly-linked list.\n",
    "# class ListNode:\n",
    "#     def __init__(self, x):\n",
    "#         self.val = x\n",
    "#         self.next = None\n",
    "\n",
    "class Solution:\n",
    "    def partition(self, head, x):\n",
    "        \"\"\"\n",
    "        :type head: ListNode\n",
    "        :type x: int\n",
    "        :rtype: ListNode\n",
    "        \"\"\"\n",
    "        lowList=[]\n",
    "        upList=[]\n",
    "\n",
    "        def searchList(listNode, x):\n",
    "            if listNode:\n",
    "                curVal = listNode.val\n",
    "                if curVal < x:\n",
    "                    #print(curVal)\n",
    "                    lowList.append(curVal)\n",
    "                else :\n",
    "                    upList.append(curVal)\n",
    "                searchList(listNode.next, x)\n",
    "\n",
    "        def replaceList(head, level=0):\n",
    "            if head:\n",
    "                head.val = lowList[level]\n",
    "                replaceList(head.next, level+1)                    \n",
    "        searchList(head, x)\n",
    "        lowList.extend(upList)\n",
    "        replaceList(head)\n",
    "        return head\n",
    "       # def replaceList(head, level=0):\n",
    "       #     if head:\n",
    "       #         head.val = newList[level]\n",
    "       #         replaceList(head.next, level+1)\n",
    "                \n",
    "        #replaceList(head)\n",
    "        "
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "from typing import List\n",
    "import collections\n",
    "\n",
    "# Definition for singly-linked list.\n",
    "# class ListNode:\n",
    "#     def __init__(self, x):\n",
    "#         self.val = x\n",
    "#         self.next = None\n",
    "\n",
    "class Solution:\n",
    "    def partition(self, head, x):\n",
    "        \"\"\"\n",
    "        :type head: ListNode\n",
    "        :type x: int\n",
    "        :rtype: ListNode\n",
    "        \"\"\"\n",
    "\n",
    "        if head is None or head.next is None or x is None:\n",
    "            return head\n",
    "        \n",
    "        p1=head1=ListNode(0)\n",
    "        p2=head2=ListNode(0)\n",
    "        p=head\n",
    "        \n",
    "        while p:\n",
    "            if p.val<x:\n",
    "                p1.next=p\n",
    "                p1=p1.next\n",
    "            else:\n",
    "                p2.next=p\n",
    "                p2=p2.next\n",
    "            p=p.next\n",
    "        p1.next=head2.next\n",
    "        p2.next=None\n",
    "        return head1.next\n",
    "\n",
    "                "
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "from typing import List\n",
    "import collections\n",
    "\n",
    "# Definition for singly-linked list.\n",
    "# class ListNode:\n",
    "#     def __init__(self, x):\n",
    "#         self.val = x\n",
    "#         self.next = None\n",
    "\n",
    "class Solution:\n",
    "    def partition(self, head: ListNode, x: int) -> ListNode:\n",
    "        high=ListNode('high')\n",
    "        high_pre=high\n",
    "        low=ListNode('low')\n",
    "        low_pre=low\n",
    "        \n",
    "        pre=head\n",
    "        #cur=pre.next\n",
    "        #big.next=big_pre\n",
    "        #small.next=small_pre\n",
    "        while(pre!=None):\n",
    "            if(pre.val<x):\n",
    "                low_pre.next=pre\n",
    "                low_pre=low_pre.next\n",
    "            else:\n",
    "                high_pre.next=pre\n",
    "                high_pre=high_pre.next\n",
    "            pre=pre.next\n",
    "        high_pre.next=None\n",
    "        low_pre.next=high.next\n",
    "        return low.next"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "from typing import List\n",
    "import collections\n",
    "\n",
    "# Definition for singly-linked list.\n",
    "# class ListNode:\n",
    "#     def __init__(self, x):\n",
    "#         self.val = x\n",
    "#         self.next = None\n",
    "\n",
    "class Solution:\n",
    "    def partition(self, head: ListNode, x: int) -> ListNode:\n",
    "        l, r = ListNode(0), ListNode(0)\n",
    "        L, R = l, r\n",
    "        while head:\n",
    "            if head.val < x:\n",
    "                l.next = head\n",
    "                l = l.next\n",
    "            else:\n",
    "                r.next = head\n",
    "                r = r.next\n",
    "            head = head.next\n",
    "        r.next = None\n",
    "        l.next = R.next\n",
    "        return L.next        "
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "from typing import List\n",
    "import collections\n",
    "\n",
    "# Definition for singly-linked list.\n",
    "# class ListNode:\n",
    "#     def __init__(self, x):\n",
    "#         self.val = x\n",
    "#         self.next = None\n",
    "\n",
    "class Solution:\n",
    "    def partition(self, head, x):\n",
    "        \"\"\"\n",
    "        :type head: ListNode\n",
    "        :type x: int\n",
    "        :rtype: ListNode\n",
    "        \"\"\"\n",
    "        lnode = None\n",
    "        rnode = None\n",
    "        frnode = None\n",
    "        ans = None\n",
    "        node = head\n",
    "        limit = 1000\n",
    "        while node and limit>0:\n",
    "            limit -= 1\n",
    "            if node.val < x:\n",
    "                if not lnode:\n",
    "                    ans = node\n",
    "                    lnode = node\n",
    "                else:\n",
    "                    lnode.next = node\n",
    "                    lnode = lnode.next\n",
    "                print(lnode.val, node.val)\n",
    "            else:\n",
    "                if not frnode:\n",
    "                    frnode = node\n",
    "                    rnode = node\n",
    "                else:\n",
    "                    rnode.next = node\n",
    "                    rnode = rnode.next\n",
    "                print(frnode.val, rnode.val, node.val)\n",
    "            node = node.next\n",
    "        \n",
    "        if frnode and lnode:\n",
    "            lnode.next = frnode\n",
    "        if rnode:\n",
    "            rnode.next = None\n",
    "        #return\n",
    "        if ans:\n",
    "            return ans\n",
    "        return head\n",
    "        "
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "from typing import List\n",
    "import collections\n",
    "\n",
    "# Definition for singly-linked list.\n",
    "# class ListNode:\n",
    "#     def __init__(self, x):\n",
    "#         self.val = x\n",
    "#         self.next = None\n",
    "\n",
    "class Solution:\n",
    "    def partition(self, head: 'ListNode', x: 'int') -> 'ListNode':\n",
    "        start = head\n",
    "        left = ListNode(0)\n",
    "        l=left\n",
    "        right =ListNode(0)\n",
    "        r = right\n",
    "        while(start):\n",
    "            if start.val < x:\n",
    "                left.next = start\n",
    "                left = left.next\n",
    "            else:\n",
    "                right.next = start\n",
    "                right = right.next\n",
    "            start = start.next\n",
    "        right.next=None\n",
    "        left.next = r.next\n",
    "        return l.next"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "from typing import List\n",
    "import collections\n",
    "\n",
    "# Definition for singly-linked list.\n",
    "# class ListNode:\n",
    "#     def __init__(self, x):\n",
    "#         self.val = x\n",
    "#         self.next = None\n",
    "\n",
    "class Solution:\n",
    "    def partition(self, head: ListNode, x: int) -> ListNode:\n",
    "        before = before_head = ListNode(0)\n",
    "        after = after_head = ListNode(0)\n",
    "        while head:\n",
    "            if head.val < x:\n",
    "                before.next = head\n",
    "                before = before.next\n",
    "            else:\n",
    "                after.next = head\n",
    "                after = after.next\n",
    "            head = head.next\n",
    "        after.next = None\n",
    "        before.next = after_head.next\n",
    "        return before_head.next"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "from typing import List\n",
    "import collections\n",
    "\n",
    "# Definition for singly-linked list.\n",
    "# class ListNode:\n",
    "#     def __init__(self, x):\n",
    "#         self.val = x\n",
    "#         self.next = None\n",
    "\n",
    "class Solution:\n",
    "    def partition(self, head: ListNode, x: int) -> ListNode:\n",
    "        less = lp = None\n",
    "        more = mp = None\n",
    "        while head:\n",
    "            if head.val < x:\n",
    "                if less:\n",
    "                    lp.next = head\n",
    "                else:\n",
    "                    less = head\n",
    "                lp = head\n",
    "            else:\n",
    "                if more:\n",
    "                    mp.next = head\n",
    "                else:\n",
    "                    more = head\n",
    "                mp = head\n",
    "            head = head.next\n",
    "        if mp:\n",
    "            mp.next = None\n",
    "        if lp:\n",
    "            lp.next = more\n",
    "        return less or more\n",
    "\n"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "from typing import List\n",
    "import collections\n",
    "\n",
    "# Definition for singly-linked list.\n",
    "# class ListNode:\n",
    "#     def __init__(self, x):\n",
    "#         self.val = x\n",
    "#         self.next = None\n",
    "\n",
    "class Solution:\n",
    "    def partition(self, head: ListNode, x: int) -> ListNode:\n",
    "        if head is None:\n",
    "            return None\n",
    "        dummy = ListNode(x-1)\n",
    "        dummy.next = head\n",
    "        head = dummy\n",
    "        p = head\n",
    "        while p.next is not None:\n",
    "            if p.next.val < x:\n",
    "                p = p.next\n",
    "                continue\n",
    "            q = p.next  # 下一个节点 >= x\n",
    "            while q.next is not None and q.next.val >= x:\n",
    "                q = q.next\n",
    "            if q.next is None:  # q为最后一个节点，终止\n",
    "                break\n",
    "            r = q.next\n",
    "            q.next = r.next\n",
    "            r.next = p.next\n",
    "            p.next = r\n",
    "        return head.next\n",
    "\n",
    "            "
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "from typing import List\n",
    "import collections\n",
    "\n",
    "# Definition for singly-linked list.\n",
    "# class ListNode:\n",
    "#     def __init__(self, x):\n",
    "#         self.val = x\n",
    "#         self.next = None\n",
    "\n",
    "class Solution:\n",
    "    def partition(self, head: ListNode, x: int) -> ListNode:\n",
    "        low = ListNode(0)\n",
    "        high = ListNode(0)\n",
    "        hl = low\n",
    "        hh = high\n",
    "        while head:\n",
    "            if head.val<x:\n",
    "                low.next = head\n",
    "                low = head\n",
    "            else:\n",
    "                high.next = head\n",
    "                high = head\n",
    "            head = head.next\n",
    "        high.next = None\n",
    "        if not hl.next:\n",
    "            return hh.next\n",
    "        low.next = hh.next\n",
    "        return hl.next"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "from typing import List\n",
    "import collections\n",
    "\n",
    "# Definition for singly-linked list.\n",
    "# class ListNode:\n",
    "#     def __init__(self, x):\n",
    "#         self.val = x\n",
    "#         self.next = None\n",
    "\n",
    "class Solution:\n",
    "    def partition(self, head: ListNode, x: int) -> ListNode:\n",
    "        # temp1 = ListNode(0)\n",
    "        # temp2 = ListNode(0)\n",
    "        # a = temp1\n",
    "        # b = temp2\n",
    "\n",
    "        # while head:\n",
    "        #     if head.val < x:\n",
    "        #         tem = head.next\n",
    "        #         temp1.next = head\n",
    "        #         temp1 = temp1.next\n",
    "        #         head = tem\n",
    "        #     else:\n",
    "        #         tem = head.next\n",
    "        #         temp2.next = head\n",
    "        #         temp2 = temp2.next\n",
    "        #         head = tem\n",
    "        # temp1.next = b.next\n",
    "        # return a.next\n",
    "\n",
    "        if not head:\n",
    "            return head\n",
    "        temp = ListNode(0)\n",
    "        s = temp\n",
    "        dummy = ListNode(0)\n",
    "        dummy.next = head\n",
    "        head = dummy\n",
    "        while head.next:\n",
    "            if head.next.val<x:\n",
    "                head = head.next\n",
    "            else:\n",
    "                t = head.next\n",
    "                head.next = head.next.next\n",
    "                temp.next = t\n",
    "                temp = temp.next\n",
    "        temp.next = None\n",
    "        head.next = s.next\n",
    "        return dummy.next\n",
    "\n",
    "             \n",
    "                \n"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "from typing import List\n",
    "import collections\n",
    "\n",
    "# Definition for singly-linked list.\n",
    "# class ListNode:\n",
    "#     def __init__(self, x):\n",
    "#         self.val = x\n",
    "#         self.next = None\n",
    "\n",
    "class Solution:\n",
    "    def partition(self, head: ListNode, x: int) -> ListNode:\n",
    "        small = small_start = ListNode(0)\n",
    "        large = large_start = ListNode(0)\n",
    "\n",
    "        while head:\n",
    "            if head.val < x:\n",
    "                small.next = head\n",
    "                small = small.next\n",
    "            if head.val >= x:\n",
    "                large.next = head\n",
    "                large = large.next\n",
    "            head = head.next\n",
    "        small.next = large_start.next\n",
    "        large.next = None\n",
    "        return small_start.next"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "from typing import List\n",
    "import collections\n",
    "\n",
    "# Definition for singly-linked list.\n",
    "# class ListNode:\n",
    "#     def __init__(self, x):\n",
    "#         self.val = x\n",
    "#         self.next = None\n",
    "\n",
    "class Solution:\n",
    "    def partition(self, head: ListNode, x: int) -> ListNode:\n",
    "        if head==None:\n",
    "            return head\n",
    "        target=False\n",
    "        firstLow=False\n",
    "        firstHigh=False\n",
    "        while head!=None:\n",
    "\n",
    "            if head.val<x:\n",
    "                if firstLow==False:\n",
    "                    low=ListNode()\n",
    "                    lstart=low\n",
    "                    low.val=head.val \n",
    "                    firstLow=True\n",
    "                     \n",
    "                else:\n",
    "                    p=ListNode()\n",
    "                    p.val=head.val\n",
    "                    low.next=p \n",
    "                    low=low.next\n",
    "                     \n",
    "            else:\n",
    "                if firstHigh==False:\n",
    "                    high=ListNode()\n",
    "                    hstart=high\n",
    "                    high.val=head.val \n",
    "                    firstHigh=True\n",
    "                    \n",
    "                else:\n",
    "                    p=ListNode()\n",
    "                    p.val=head.val\n",
    "                    high.next=p \n",
    "                    high=high.next\n",
    "                     \n",
    "            head=head.next\n",
    "        if firstLow==True:\n",
    "            if firstHigh==True:\n",
    "                low.next=hstart\n",
    "                return lstart\n",
    "            else:\n",
    "                return lstart\n",
    "        else:\n",
    "            return hstart"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "from typing import List\n",
    "import collections\n",
    "\n",
    "# Definition for singly-linked list.\n",
    "# class ListNode:\n",
    "#     def __init__(self, x):\n",
    "#         self.val = x\n",
    "#         self.next = None\n",
    "\n",
    "class Solution(object):\n",
    "    def partition(self, head, x):\n",
    "\n",
    "        before = before_head = ListNode(0)   # 值小于X的子链表\n",
    "        after = after_head = ListNode(0)     # 值等于大于X的子链表\n",
    "\n",
    "        while head:\n",
    "            if head.val < x:\n",
    "                before.next = head\n",
    "                before = before.next\n",
    "            else:\n",
    "                after.next = head\n",
    "                after = after.next\n",
    "            head = head.next\n",
    "\n",
    "\n",
    "        after.next = None\n",
    "        before.next = after_head.next        # 拼接两个链表\n",
    "\n",
    "        return before_head.next"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "from typing import List\n",
    "import collections\n",
    "\n",
    "# Definition for singly-linked list.\n",
    "# class ListNode:\n",
    "#     def __init__(self, x):\n",
    "#         self.val = x\n",
    "#         self.next = None\n",
    "\n",
    "class Solution:\n",
    "    def partition(self, head: ListNode, x: int) -> ListNode:\n",
    "        currentNode = head\n",
    "        little = None\n",
    "        littleCurrent = None\n",
    "        big = None\n",
    "        bigCurrent = None\n",
    "        while currentNode:\n",
    "            print(currentNode.val)\n",
    "            if currentNode.val<x:\n",
    "                if little:\n",
    "                    littleCurrent.next = currentNode\n",
    "                    littleCurrent = currentNode\n",
    "                else:\n",
    "                    little = currentNode\n",
    "                    littleCurrent = currentNode\n",
    "            else:\n",
    "                if big:\n",
    "                    bigCurrent.next = currentNode\n",
    "                    bigCurrent = currentNode\n",
    "                else:\n",
    "                    big = currentNode\n",
    "                    bigCurrent = currentNode\n",
    "            currentNode = currentNode.next\n",
    "            if littleCurrent:littleCurrent.next = None\n",
    "            if bigCurrent:bigCurrent.next = None\n",
    "\n",
    "        if littleCurrent:\n",
    "            littleCurrent.next = big\n",
    "            return little\n",
    "        else:\n",
    "            return big\n",
    "        "
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "from typing import List\n",
    "import collections\n",
    "\n",
    "# Definition for singly-linked list.\n",
    "# class ListNode:\n",
    "#     def __init__(self, x):\n",
    "#         self.val = x\n",
    "#         self.next = None\n",
    "\n",
    "def printlist(head):\n",
    "    while head:\n",
    "        print(head.val, end = ' ')\n",
    "        head = head.next\n",
    "    print('')\n",
    "\n",
    "class Solution:\n",
    "    def partition(self, head: ListNode, x: int) -> ListNode:\n",
    "        \n",
    "        sentinel = ListNode(0)\n",
    "        sentinel.next = head\n",
    "        \n",
    "        rp = sentinel\n",
    "        \n",
    "        p = head\n",
    "        pre = sentinel\n",
    "        \n",
    "        while p:\n",
    "            if p.val < x:\n",
    "                    \n",
    "                # print(p.val)\n",
    "                # print(pre.val)\n",
    "                # print(rp.val)\n",
    "                if rp == pre:\n",
    "                    p = p.next\n",
    "                    pre = pre.next\n",
    "                    rp = rp.next\n",
    "                else:    \n",
    "                    pre.next = p.next\n",
    "                    p.next = rp.next\n",
    "                    rp.next = p\n",
    "\n",
    "\n",
    "                    p = pre.next\n",
    "                    rp = rp.next\n",
    "                # print(p.val)\n",
    "                # print(pre.val)\n",
    "                # print(rp.val)\n",
    "               \n",
    "                \n",
    "            else:\n",
    "                p = p.next\n",
    "                pre = pre.next\n",
    "            printlist(sentinel.next)\n",
    "            \n",
    "        return sentinel.next\n",
    "                "
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "from typing import List\n",
    "import collections\n",
    "\n",
    "# Definition for singly-linked list.\n",
    "# class ListNode:\n",
    "#     def __init__(self, val=0, next=None):\n",
    "#         self.val = val\n",
    "#         self.next = next\n",
    "class Solution:\n",
    "    def partition(self, head: ListNode, x: int) -> ListNode:\n",
    "        l1, l2 = ListNode(None), ListNode(None)\n",
    "        cur1, cur2 = l1, l2\n",
    "        cur = head\n",
    "        while cur:\n",
    "            if cur.val < x:\n",
    "                cur1.next = ListNode(cur.val)\n",
    "                cur1 = cur1.next\n",
    "            else:\n",
    "                cur2.next = ListNode(cur.val)\n",
    "                cur2 = cur2.next\n",
    "            cur = cur.next\n",
    "        cur1.next = l2.next\n",
    "        return l1.next"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "from typing import List\n",
    "import collections\n",
    "\n",
    "# Definition for singly-linked list.\n",
    "# class ListNode:\n",
    "#     def __init__(self, val=0, next=None):\n",
    "#         self.val = val\n",
    "#         self.next = next\n",
    "class Solution:\n",
    "    def partition(self, head: Optional[ListNode], x: int) -> Optional[ListNode]:\n",
    "        dummy = ListNode(0,head)\n",
    "        pre = dummy\n",
    "        cur = pre\n",
    "        while cur.next and cur.next.val<x:\n",
    "            pre = pre.next\n",
    "            cur = cur.next\n",
    "        if not cur.next:\n",
    "            return head\n",
    "        while cur.next:\n",
    "            if cur.next.val<x:\n",
    "                 tmp = cur.next\n",
    "                 cur.next = cur.next.next\n",
    "                 tmp.next = pre.next\n",
    "                 pre.next = tmp\n",
    "                 pre = pre.next\n",
    "            else:\n",
    "                cur = cur.next \n",
    "        return dummy.next"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "from typing import List\n",
    "import collections\n",
    "\n",
    "# Definition for singly-linked list.\r\n",
    "# class ListNode:\r\n",
    "#     def __init__(self, val=0, next=None):\r\n",
    "#         self.val = val\r\n",
    "#         self.next = next\r\n",
    "class Solution:\r\n",
    "    def partition(self, head: Optional[ListNode], x: int) -> Optional[ListNode]:\r\n",
    "        lo_head = ListNode()\r\n",
    "        hi_head = ListNode()\r\n",
    "\r\n",
    "        lo_cur = lo_head\r\n",
    "        hi_cur = hi_head\r\n",
    "\r\n",
    "        cur = head\r\n",
    "        while cur:\r\n",
    "            if cur.val < x:\r\n",
    "                lo_cur.next = cur\r\n",
    "                lo_cur = cur\r\n",
    "                cur = cur.next\r\n",
    "                lo_cur.next = None\r\n",
    "            else:\r\n",
    "                hi_cur.next = cur\r\n",
    "                hi_cur = cur\r\n",
    "                cur = cur.next\r\n",
    "                hi_cur.next = None\r\n",
    "\r\n",
    "        lo_cur.next = hi_head.next\r\n",
    "        return lo_head.next\r\n",
    "\r\n"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "from typing import List\n",
    "import collections\n",
    "\n",
    "# Definition for singly-linked list.\n",
    "# class ListNode:\n",
    "#     def __init__(self, val=0, next=None):\n",
    "#         self.val = val\n",
    "#         self.next = next\n",
    "class Solution:\n",
    "    def partition(self, head: Optional[ListNode], x: int) -> Optional[ListNode]:\n",
    "        dummy1=ListNode(-1)\n",
    "        dummy2=ListNode(-1)\n",
    "\n",
    "        p1=dummy1\n",
    "        p2=dummy2\n",
    "        \n",
    "        p=head\n",
    "        while p:\n",
    "            if p.val<x:\n",
    "                p1.next=p\n",
    "                p1=p1.next\n",
    "            else:\n",
    "                p2.next=p\n",
    "                p2=p2.next\n",
    "\n",
    "            temp=p.next\n",
    "            p.next=None\n",
    "            p=temp\n",
    "              \n",
    "        p1.next=dummy2.next\n",
    "        return dummy1.next\n",
    "\n",
    " \n",
    "\n",
    "\n"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "from typing import List\n",
    "import collections\n",
    "\n",
    "# Definition for singly-linked list.\n",
    "# class ListNode:\n",
    "#     def __init__(self, val=0, next=None):\n",
    "#         self.val = val\n",
    "#         self.next = next\n",
    "class Solution:\n",
    "    def partition(self, head: ListNode, x: int) -> ListNode:\n",
    "        dummy1 = ListNode(-1)\n",
    "        dummy2 = ListNode(-2)\n",
    "        p1, p2 = dummy1, dummy2 # p1, p2 指针负责生成结果链表\n",
    "\n",
    "        p = head # p负责遍历原链表，类似合并两个有序链表的逻辑\n",
    "        while p:\n",
    "            if p.val < x:\n",
    "                p1.next = p\n",
    "                p1 = p1.next\n",
    "                print(\"p1: \", p1.val) \n",
    "            else:\n",
    "                p2.next = p\n",
    "                p2 = p2.next\n",
    "                print(\"p2: \", p2.val) \n",
    "            \n",
    "            # 将当前节点的next指针清空，避免链表中存在环 （断开原链表中的每个节点的 next 指针）\n",
    "            temp = p.next\n",
    "            p.next  = None\n",
    "            # 继续向下遍历原链表\n",
    "            p = temp\n",
    "\n",
    "        p1.next = dummy2.next # 连接两个链表\n",
    "        return dummy1.next"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "from typing import List\n",
    "import collections\n",
    "\n",
    "# Definition for singly-linked list.\n",
    "# class ListNode:\n",
    "#     def __init__(self, val=0, next=None):\n",
    "#         self.val = val\n",
    "#         self.next = next\n",
    "class Solution:\n",
    "    def partition(self, head: Optional[ListNode], x: int) -> Optional[ListNode]:\n",
    "        if head is None or head.next is None:\n",
    "            return head\n",
    "        h1 = ListNode()\n",
    "        h2 = ListNode()\n",
    "\n",
    "        cur_node = head\n",
    "        p1 = h1\n",
    "        p2 = h2\n",
    "        while cur_node:\n",
    "            print(\"cur_node\", cur_node)\n",
    "            print(\"p1:\", p1)\n",
    "            print(\"p2:\", p2)\n",
    "\n",
    "            if cur_node.val < x:\n",
    "                p1.next = cur_node\n",
    "                p1 = p1.next\n",
    "            else:\n",
    "                p2.next = cur_node\n",
    "                p2 = p2.next\n",
    "\n",
    "            cur_node = cur_node.next\n",
    "            p1.next = None\n",
    "            p2.next = None\n",
    "            \n",
    "            \n",
    "        print(\"h1:\", h1)\n",
    "        print(\"h2:\", h2)\n",
    "        print(\"p1:\", p1)\n",
    "        p1.next = h2.next\n",
    "\n",
    "        return h1.next"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "from typing import List\n",
    "import collections\n",
    "\n",
    "# Definition for singly-linked list.\n",
    "# class ListNode:\n",
    "#     def __init__(self, val=0, next=None):\n",
    "#         self.val = val\n",
    "#         self.next = next\n",
    "class Solution:\n",
    "    def partition(self, head: Optional[ListNode], x: int) -> Optional[ListNode]:\n",
    "        if not head:\n",
    "            return head\n",
    "        \n",
    "        small_partition = small_head = ListNode(0)\n",
    "        large_partition = large_head = ListNode(0)\n",
    "        curr = head\n",
    "        while curr:\n",
    "            if curr.val < x:\n",
    "                small_head.next = curr\n",
    "                small_head = small_head.next\n",
    "            else:\n",
    "                large_head.next = curr\n",
    "                large_head = large_head.next\n",
    "            curr = curr.next\n",
    "        small_head.next = large_partition.next\n",
    "        large_head.next = None\n",
    "\n",
    "        return small_partition.next"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "from typing import List\n",
    "import collections\n",
    "\n",
    "# Definition for singly-linked list.\n",
    "# class ListNode:\n",
    "#     def __init__(self, val=0, next=None):\n",
    "#         self.val = val\n",
    "#         self.next = next\n",
    "class Solution:\n",
    "    def partition(self, head: Optional[ListNode], x: int) -> Optional[ListNode]:\n",
    "        if not head:\n",
    "            return\n",
    "        # dummy1链表存放小于x的节点，dummy2链表存放大于或等于x的节点\n",
    "        dummy1, dummy2 = ListNode(-1), ListNode(-1)\n",
    "        p1, p2 = dummy1, dummy2\n",
    "        while head:\n",
    "            if head.val < x:\n",
    "                p1.next = head\n",
    "                p1 = p1.next\n",
    "            else:\n",
    "                p2.next = head\n",
    "                p2 = p2.next\n",
    "            head = head.next\n",
    "        # 拼接链表\n",
    "        p1.next = dummy2.next\n",
    "        p2.next = None\n",
    "        return dummy1.next"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "from typing import List\n",
    "import collections\n",
    "\n",
    "# Definition for singly-linked list.\n",
    "# class ListNode:\n",
    "#     def __init__(self, val=0, next=None):\n",
    "#         self.val = val\n",
    "#         self.next = next\n",
    "class Solution:\n",
    "    def partition(self, head: Optional[ListNode], x: int) -> Optional[ListNode]:\n",
    "        small = ListNode(0)\n",
    "        small_head = small\n",
    "        large = ListNode(0)\n",
    "        large_head = large\n",
    "\n",
    "        while head:\n",
    "            if head.val < x:\n",
    "                small.next = head\n",
    "                small = small.next\n",
    "            else:\n",
    "                large.next = head\n",
    "                large = large.next\n",
    "        \n",
    "            head=head.next\n",
    "\n",
    "        large.next=None\n",
    "        small.next = large_head.next\n",
    "\n",
    "        return small_head.next\n"
   ]
  }
 ],
 "metadata": {},
 "nbformat": 4,
 "nbformat_minor": 2
}
